require 'bdb'
require 'uconv'
require 'singleton'
+require 'rbchise'
+require 'db'
+require 'ids'
$KCODE = 'u' #今のところこれ以外では動かない。String.splitが影響大。inspectも影響。
$debug = false #これはテスト用
def char_at(n) to_a()[n] end
def char() Character.get(to_a[0]) end
#alias to_c char #悩み中
- def char_id() char.char_id() end
- def get_char_attribute(a) char.get_char_attribute(a) end
+ #def char_id() char.char_id() end #なんとなく廃止
+ #def get_char_attribute(a) char.get_char_attribute(a) end #なんとなく廃止
#def ucs() char.ucs() end
def to_utf8()
return to_a.map {|ch|
module_function :windows?
if windows?()
DB_DIR = 'd:/work/chise/char-db' #この後に/sysmtem-char-id/ucsという感じに続く
+ IDS_DB_DIR = 'd:/work/chise/ids/' #この後にIDS-JIS-X0208-1990.txtという感じに続く
else
DB_DIR = '/usr/local/lib/xemacs-21.4.10/i686-pc-linux/char-db' #この後に/sysmtem-char-id/ucsという感じに続く
+ IDS_DB_DIR = '/home/eto/work/chise/ids/' #この後にIDS-JIS-X0208-1990.txtという感じに続く
end
class EntityReference #======================================================================
end
class Character #=============================================================== 文字オブジェクト
- BASIC_KANJI = "人子女母父王口耳手足力目首毛心犬牛鳥貝角羽虫馬魚羊肉皮米竹木麦豆山川雨風水土石金田穴日月火音糸刀舟門戸衣矢弓車皿一二三四五六七八九十百千万寸尺上中下本玉立回食行止交向歩考入示走生出来書言大小白青多少高長"
- def is_basic_kanji?
- BASIC_KANJI.include?(self.to_s)
- end
-
def initialize(char_id=nil)
@char_id = Character.parse_char_id(char_id)
@attributes = Hash.new
alist.to_a.sort.each {|a, v| ar << "#{a}:#{v}" }
return ar.join(',')+">"
end
+ def dump_all()
+ ar = [inspect]
+ alist.to_a.sort.each {|a, v| ar << "#{a}:#{v}" }
+ return ar.join('\n')+'\n'
+ end
def get_attributes()
str = ""
alist.to_a.sort.each {|a, v|
end
end
- class DBS #======================================================================複数のDBを集めたclass、未完成
- end
-
- class ADB < BDB::Hash #======================================================================一つのDB
- def initialize(*args)
- super
- @modified = false
- at_exit {
- if @modified
- self.close #これがないと、うまくデータベースがセーブされないのです。
- end
- }
- end
- def self.open_create(filename)
- ADB.open(filename, nil, BDB::CREATE | BDB::EXCL) #上書きはしない
- end
- def mykey(key)
- if key.is_a?(String)
- if key.char_length == 1
- return '?'+key #Stringだったら引く前に?を足す
- end
- end
- #key = key.to_s if key.is_a?(Numeric) #NumberだったらStringにする。
- #ここで && key ! =~ /^\?/ をいれると、?自身を検索できなくなってしまう。
- return key
- end
- def myvalue(v)
- return v if v == nil
- return v.to_i if v =~ /^\d+$/ #数字だったらここで変換しておく
- return v.sub(/^\?/, '') if v =~ /^\?/ #冒頭の?は取り除く
- return $1 if v =~ /^"(.+)"$/ #最初と最後に"がついていたら、取り除く
- #p ['get', v, t, key, db]
- #return parse_sexp(v) if v =~ /^\(.+\)$/ #最初と最後が()の時は、S式にparseする
- return v #それ以外って何?
- end
- def myget(key) #keyキーを引いて返す
- key = mykey(key)
- v = get(key) #存在しなかったらnilを返すことになる
- return myvalue(v)
- end
- def myput(key, v) #keyにvをいれる
- key = mykey(key)
- put(key, v) #putする
- @modified = true
- end
- end
-
- class DB #======================================================= データベース群のabstract class
- def self.unix_to_win(unix) #Windowsファイル名制限のため、変換する
- win = unix.gsub(/</, '(')
- win.gsub!(/>/, ')')
- win.gsub!(/\*/, '+')
- win.gsub!(/\?/, '!')
- return win
- end
- def self.win_to_unix(win)
- unix = win.gsub(%r|\)|, '>')
- unix.gsub!(%r|\(|, '<')
- unix.gsub!(%r|!|, '?')
- unix.gsub!(%r|\+|, '*')
- return unix
- end
- def get_filename(t)
- return @pre + DB.unix_to_win(t) + @post if windows?
- return @pre + t + @post
- end
- def get_dirname(t) File.dirname(get_filename(t)) end
- def open_dbs()
- @dbs = Hash.new
- keys = find_keys()
- keys.each {|key| open_db(key) }
- end
- def find_keys()
- files = []
- Dir.glob(@glob){|f|
- next if ! File.file?(f)
- next if f =~ /.txt$/
- files << f
- }
- keys = []
- files.each {|f|
- t = DB.win_to_unix(f)
- t.sub!(%r|^#{@pre}|, '')
- t.sub!(%r|#{@post}$|, '') if @post != ""
- keys << t
- }
- return keys
- end
- def close_db(t)
- db = get(t)
- return nil if db.nil?
- db.close
- @dbs.delete(t)
- end
- def open_db(t)
- return nil if get(t) #すでにopenしていたら再openはしない。
- begin
- bdb = ADB.open(get_filename(t), nil, 0)
- @dbs[t] = bdb if bdb != nil
- rescue
- p ["open error", get_filename(t)]; return nil
- end
- return true
- end
- def make_db(t, h=nil) #tという名前でhという中身のデータベースを作る
- return nil if get(t) #すでにある場合はreturn
- Dir.mkdir(get_dirname(t)) unless FileTest.exist?(get_dirname(t))
- db = nil
- begin
- db = ADB.open_create(get_filename(t)) #上書きはしない
- if h != nil
- h.each {|k, v|
- k = '?'+k if k.is_a?(String)
- db[k] = v
- }
- end
- db.close
- rescue
- p ["make error", get_filename(t)]; return nil
- end
- return true
- end
- def make_db_no_question_mark(t, h=nil) #tという名前でhという中身のデータベースを作る
- return nil if get(t) #すでにある場合はreturn
- Dir.mkdir(get_dirname(t)) unless FileTest.exist?(get_dirname(t))
- db = nil
- begin
- db = ADB.open_create(get_filename(t)) #上書きはしない
- if h != nil
- h.each {|k, v|
- # k = '?'+k if k.is_a?(String)
- db[k] = v
- }
- end
- db.close
- rescue
- p ["make error", get_filename(t)]; return nil
- end
- return true
- end
- def remove_db(t) #tという名前のデータベースを消去する
- db = get(t)
- if db
- db.close
- @dbs.delete(t)
- end
- begin
- File.unlink(get_filename(t)) if FileTest.file?(get_filename(t))
- rescue
- p ["unlink error", get_filename(t)]; return nil
- end
- dn = get_dirname(t)
- Dir.rmdir(dn) if FileTest.directory?(dn) && Dir.entries(dn).length <= 2 #空directoryだったら消す
- return true
- end
- def to_num(s)
- return s.to_i if s =~ /^\d+$/
- return s
- end
- def dump_db(t)
- db = get(t)
- return nil unless db
- file = get_filename(t)
- open("#{file}.txt", "w"){|out|
- # out.binmode.sync = true
- ar = db.to_a
- ar.map! {|k, v| [to_num(k), to_num(v)] }
- ar.sort.each {|k, v|
- out.printf("%s\t%s\n", k, v)
- }
- }
- return true
- end
- def each_db() @dbs.to_a.sort.each {|t, db| yield(t, db) } end
- def dump_all() each_db {|t, db| dump_db(t) } end
- def close_all() each_db {|t, db| db.close } end
- def keys() @dbs.keys end
- def each(t)
- return unless block_given?
- db = @dbs[t]
- return nil unless db
- db.each {|k, v|
- k = to_num(k)
- v = to_num(v)
- k.sub!(/^\?/, '') if k =~ /^\?/ #冒頭の?は取り除く
- vv = get(t, k) #p ['each', t, k, v, vv]
- yield(k, vv)
- }
- end
- def each_sort(t)
- return unless block_given?
- db = @dbs[t]
- return nil unless db
- ar = db.to_a
- ar.map! {|k, v| [to_num(k), to_num(v)] }
- ar.sort.each {|k, v|
- k.sub!(/^\?/, '') if k =~ /^\?/ #冒頭の?は取り除く
- vv = get(t, k) #p ['each', t, k, v, vv]
- yield(k, vv)
- }
- end
- #----------------------------------------------------------------------
- def get(t, key=nil) #tというデータベースのkeyキーを引いて返す
- db = @dbs[t]
- return db if key.nil?
- return nil unless db
- return db.myget(key)
- end
- def put(t, key, v) #tというデータベースのkeyにvをいれる
- db = @dbs[t]
- if db == nil
- db = make_db(t)
- db = open_db(t)
- db = @dbs[t]
- end
- db.myput(key, v) #putする
- end
- end
-
- class CharDB < DB #------------------------------------ MCS-UTF8をキーとした属性へのデータベース
- include Singleton
- def initialize()
- super
- @glob, @pre, @post = "#{DB_DIR}/system-char-id/*", "#{DB_DIR}/system-char-id/", ""
- open_dbs()
- end
- def get_all(u8) #全データベースのu8キーを引いてHashにまとめて返す
- atrs = Hash.new
- @dbs.each {|t, db|
- v = get(t, u8)
- atrs[t] = v if v != nil
- }
- return atrs
- end
- end
-
- class CodesysDB < DB #----------------------------------------------------------------------
- include Singleton
- def initialize()
- super
- @glob, @pre, @post = "#{DB_DIR}/*/system-char-id", "#{DB_DIR}/", "/system-char-id"
- open_dbs()
- end
- #def keys() @dbs.keys.sort end #どんなCodesysの情報を持っているかの一覧
- def keys() @dbs.keys end #どんなCodesysの情報を持っているかの一覧
- def get_codesys(t)
- db = get(t)
- return nil unless db
- return Codesys.new(t)
- end
- end
-
- class Codesys < DB #======================================================================
- def initialize(name)
- # super
- @name = name
- @dbs = CodesysDB.instance
- end
- def keys() #どんなコードポイントの情報を持っているかの一覧
- ks = @dbs.get(@name).keys
- if @name =~ /jisx0208/ #特別処理
- n = @dbs.get('=jis-x0208').keys
- # p ['keys', @name, ks, n]
- ks += n
- end
- ks.map! {|k| to_num(k) }
- ks
- end
- def get(key)
- v = @dbs.get(@name, key)
- return v if v
- if @name =~ /jisx0208/ #jisx0208が含まれている場合だけ特別処理する
- return @dbs.get('=jis-x0208', key)
- end
- return nil
- end
- def each()
- return unless block_given?
- db = @dbs.get(@name)
- return nil unless db
- db.each {|k, v|
- k = to_num(k)
- v = to_num(v)
- k.sub!(/^\?/, '') if k =~ /^\?/ #冒頭の?は取り除く
- vv = @dbs.get(@name, k) #p ['each', t, k, v, vv]
- yield(k, vv)
- }
- end
- def each_sort()
- return unless block_given?
- db = @dbs.get(@name)
- return nil unless db
- ar = db.to_a
- ar.map! {|k, v| [to_num(k), to_num(v)] }
- ar.sort.each {|k, v|
- k.sub!(/^\?/, '') if k =~ /^\?/ #冒頭の?は取り除く
- vv = @dbs.get(@name, k) #p ['each', t, k, v, vv]
- yield(k, vv)
- }
- end
- end
-
- class JISX0208
- def initialize
- db = CodesysDB.instance
- @common = db.get_codesys('=jis-x0208')
- @newest = db.get_codesys('japanese-jisx0208-1990')
- end
- def get_char(code)
- char = @common.get(code)
- return char unless char.nil?
- char = @newest.get(code)
- return char unless char.nil?
- return nil
- end
- end
-
- class IDS_TEXT_DB < DB #======================================================================
- include Singleton
- if CHISE.windows?()
- IDS_DB_DIR = 'd:/work/chise/ids/' #この後にIDS-JIS-X0208-1990.txtという感じに続く
- else
- IDS_DB_DIR = '/home/eto/work/chise/ids/' #この後にIDS-JIS-X0208-1990.txtという感じに続く
- end
- IDS_LIST = "
-IDS-UCS-Basic.txt
-#IDS-UCS-Compat-Supplement.txt
-#IDS-UCS-Compat.txt
-IDS-UCS-Ext-A.txt
-IDS-UCS-Ext-B-1.txt
-IDS-UCS-Ext-B-2.txt
-IDS-UCS-Ext-B-3.txt
-IDS-UCS-Ext-B-4.txt
-IDS-UCS-Ext-B-5.txt
-IDS-UCS-Ext-B-6.txt
-IDS-JIS-X0208-1990.txt
-IDS-Daikanwa-01.txt
-IDS-Daikanwa-02.txt
-IDS-Daikanwa-03.txt
-IDS-Daikanwa-04.txt
-IDS-Daikanwa-05.txt
-IDS-Daikanwa-06.txt
-IDS-Daikanwa-07.txt
-IDS-Daikanwa-08.txt
-IDS-Daikanwa-09.txt
-IDS-Daikanwa-10.txt
-IDS-Daikanwa-11.txt
-IDS-Daikanwa-12.txt
-IDS-Daikanwa-dx.txt
-IDS-Daikanwa-ho.txt
-IDS-CBETA.txt
-".split
- def initialize()
- super
- @ids_list = IDS_LIST
- @chars = []
- @glob, @pre, @post = "#{IDS_DB_DIR}/db/*", "#{IDS_DB_DIR}/db/", ""
- dir = File.dirname(@pre)
- Dir.mkdir(dir) unless FileTest.exist?(dir)
- open_dbs()
- end
- def each_file()
- return unless block_given?
- @ids_list.each {|file|
- next if file =~ /^#/
- yield(IDS_DB_DIR+file)
- }
- end
- def each_line(file)
- open(file){|f|
- while line = f.gets
- next if line =~ /^;/ #コメントはとばす
- line.chomp!
- code, char, ids = line.split
- yield(code, char, ids)
- end
- }
- end
- def dump_text_all
- each_file {|file|
- dir = File.dirname(file) + '/../ids-new/'
- Dir.mkdir(dir) if ! FileTest.directory?(dir)
- newfile = dir + File.basename(file)
- p [file, newfile]
- open(newfile, "w"){|out|
- out.binmode.sync = true
- each_line(file){|code, ch, ids|
- char = Character.get(ch)
- ids = char.decompose
- out.print "#{code} #{ch} #{ids}\n"
- }
- }
- }
- end
- def make_ids_error
- each_file {|file|
- dir = File.dirname(file) + '/../ids-error'
- Dir.mkdir(dir) unless FileTest.exist?(dir)
- errfile = dir + '/' + File.basename(file)
- # p [file, errfile]
- open(errfile, "w"){|out|
- out.binmode.sync = true
- each_line(file){|code, ch, ids|
- char = Character.get(ch)
- ids_error = char['ids-error']
- next if ids_error.nil?
- out.print "#{code} #{ch} #{ids} #{ids_error}\n"
- }
- }
- }
- end
- end
-
- class IDS_DB < DB #======================================================================BDB化したIDS DBを扱う
- include Singleton
- def initialize
- @dbs = CharDB.instance
- end
- def make_ids_db
- db = IDS_TEXT_DB.instance
- db.each_file {|file|
- @char_counter = 0
- @same_ids_counter = 0
- @good_ids_counter = 0
- @conflict_ids_counter = 0
- db.each_line(file){|code, ch, ids|
- @char_counter += 1
-
- ids = "" if ids == nil
- next if ids == "" #IDSが定義されていない場合は、さっくりと無視するべしよ。
-
- charimg = Character.get(ch) #実体参照である可能性がある
-
- next if code =~ /'$/ || code =~ /"$/ #大漢和番号のダッシュ付きは無視する
- char = Character.get("&"+code+";") #code表記を元に実体参照を作って解釈する
- if char.nil? || char.to_s == "" #うまく文字にならなかった
- print "char == null #{char.inspect} #{code} #{ch} #{ids}\n" unless code =~ /^M-/ || code =~ /^CB/
- #大漢和、CBETA以外の場合は、エラーメッセージ。
- next
- end
- if char != charimg #code表記と文字が一致していない?
- unless code =~ /^M-/ || code =~ /^MH-/ || code =~ /^CB/ #食い違っていて当然であるので何もしない
- print "unknown char #{char.inspect} #{code} #{ch} #{ids}\n"
- next #それ以外の場合はエラーメッセージをだして、次へ。
- end
- end
- #next if !char.has_attribute? #isolated characterはまぎれこませない。
-
- ids.de_er! #実体参照を解除する
- next if ids == char.to_s #もし文字とまったく一緒なら、意味が無いので情報を持たない
- next if ids.char_length == 1
-
- idstree = IDS_Tree.new(ids)
- c = idstree.check_integrity
- c = "contains self" if ids.include?(char.to_s)
- if c #ちょっとでもエラーがある場合は、
- char['ids-error'] = c #エラーを記録して、データとしては保持しない
- next
- end
-
- if char['ids'].nil? || char['ids'] == "" #元々IDSが無かった場合は、
- char['ids'] = ids #普通に代入すればそれでいいです。
- @good_ids_counter += 1
- else #しかしいままでにすでにIDSが定義されていた場合は?
- if char['ids'] == ids #新しいIDSと古いIDSが完全に一致するなら無視しましょう。
- @same_ids_counter += 1
- else #しかしいままでのIDSと新しいIDSが食い違った場合は?
- @conflict_ids_counter += 1
- # print "conflict #{char.inspect} #{code} #{ids} #{char['ids']}\n"
- end
- end
- }
- print "#{file} #{@char_counter} #{@same_ids_counter} #{@conflict_ids_counter} #{@good_ids_counter}\n"
- CharacterFactory.instance.reset()
- }
- @dbs.dump_db('ids-error') #テキスト化する
- @dbs.dump_db('ids') #テキスト化する
- end
- def make_ids_reverse
- h = Hash.new
- @dbs.each('ids') {|k, v|
- char = k.char
- ids = char.decompose
- h[ids] = "" if h[ids].nil?
- h[ids] += k #追加する
- }
- h.each {|k, v|
- h[k] = char_sort(v) #文字の順番を、よく使うっぽいものからの順番にする
- }
- h.delete_if {|k, v| #h[k]が""になる可能性もあるが、それはkeyとして入れないことにする。
- v == ""
- }
- print "length #{h.length}\n"
- cdb = CodesysDB.instance
- cdb.make_db_no_question_mark('ids', h)
- cdb.open_db('ids') #これが無いと、dump_dbされません。
- cdb.dump_db('ids')
- end
- def char_sort(composed)
- return composed if composed.char_length == 1
- ar = composed.to_a
- arorg = ar.dup
- ar2 = []
- ar.dup.each {|ch|
- char = ch.char
- if char.char_id < 0xfffff #Unicodeっぽい?
- ar2 << ch
- ar.delete(ch)
- end
- }
- if 0 < ar.length
- EntityReference.each_codesys{|codesys, er_prefix, keta, numtype|
- ar.each {|ch|
- char = ch.char
- v = char[codesys]
- # p [codesys, v] if v
- if v #EntityReferenceの順番に準拠する。
- ar2 << ch
- ar.delete(ch)
- end
- }
- }
- end
- if 0 < ar.length
- # p ['yokuwakaran character', ar, ar[0].inspect_all, arorg]
- EntityReference.each_codesys{|codesys, er_prefix, keta, numtype|
- ar.dup.each {|ch|
- char = ch.char
- v = char[codesys]
- # p [codesys, v] if v
- }
- }
- end
- return ar2.join("")
- end
- def dump_ids_duplicated
- open('ids-duplicated.txt', 'w'){|out|
- #out.binmode
- CodesysDB.instance.each('ids') {|k, v|
- if v.nil?
- out.print "nil #{k} #{v}\n"
- next
- end
- n = v.char_length
- next if n == 1
- out.print "#{n} #{k} #{v}"
- v.each_char {|ch|
- char = ch.char
- out.print " #{char.inspect}"
- }
- out.print "\n"
- }
- }
- end
- def make_ids_aggregated
- @dbs.each('ids') {|k, v|
- char = k.char
- ids = char.decompose
- ag = ids.aggregate
- char['ids-aggregated'] = ag
- }
- @dbs.dump_db('ids-aggregated')
- end
- def dump_ids_aggregated
- open('ids-aggregated.txt', 'w'){|out|
- #out.binmode
- @dbs.each('ids') {|k, v|
- char = k.char
- ids = char['ids']
- ag = char['ids-aggregated']
- out.print "#{char.to_s} #{ag} #{ids}\n" if ids != ag
- }
- }
- end
- def make_ids_parts
- @dbs.each('ids') {|k, v|
- char = k.char
- pids = char.to_s
- ar = []
- counter = 0
- loop {
- ids = pids.decompose
- break if ids == pids #これ以上分割できないようだったら終了〜。
- ar += ids.to_a
- counter += 1
- p [char.to_s, pids, ids, ar] if 10 < counter #これは何かおかしいぞと
- pids = ids
- }
- ar.sort!
- ar.uniq!
- #やっぱりIDS文字も加えることにする. by eto 2003-02-05
- # ar.delete_if {|ch|
- # ch.char.is_ids? #IDS文字はまぎれこませない。
- # }
- str = ar.join('')
- char['ids-parts'] = str
- }
- @dbs.dump_db('ids-parts')
- end
- def make_ids_contained
- h = Hash.new
- @dbs.each('ids-parts') {|k, v|
- char = k.char
- parts = char.ids_parts
- parts.each_char {|ch|
- # part = ch.char
- h[ch] = [] if h[ch].nil?
- h[ch] << k
- # h[ch] += k
- # part['ids-contained'] = "" if part['ids-contained'].nil?
- # part['ids-contained'] += k
- }
- }
- h.each {|k, v|
- char = k.char
- v.sort!
- char['ids-contained'] = v.join('')
-
- }
- @dbs.dump_db('ids-contained')
- end
- def make_ids_decomposed
- @dbs.each('ids') {|k, v|
- char = k.char
- de= char.decompose_all
- char['ids-decomposed'] = de
- }
- @dbs.dump_db('ids-decomposed')
- end
- end
-
- class Node < Array #=======================================================木構造の中の一つの枝
- def initialize(nodeleaf=nil, nodenum=nil)
- super()
- @nodeleaf = nodeleaf
- @nodenum = nodenum
- if @nodeleaf
- original_add(@nodeleaf)
- end
- end
- attr_reader :nodenum
- alias original_add <<
- private :original_add
- def <<(obj)
- original_add(obj)
- @nodenum -= 1 if @nodenum
- end
- def nodes
- ar = []
- ar << self.to_s
- self.each {|n|
- ar += n.nodes if n.is_a? Node
- }
- return ar
- end
- end
-
- class Tree #======================================================================木構造を扱う
- def initialize()
- @root = Node.new()
- @stack = [@root]
- @leafnum = 0
- @depth = 1 #stackの深さが最大になったところの値、木構造が無いときは1となる
- end
- def depth() @depth - 1 end
- def add_node(nodeleaf=nil, nodenum=nil) #枝を追加
- new_node = Node.new(nodeleaf, nodenum)
- @stack.last << new_node
- @stack << new_node
- if @depth < @stack.length
- @depth = @stack.length
- end
- self
- end
- def end_node() #この枝は終り
- @stack.pop
- self
- end
- def add_leaf(a) #葉を追加
- @stack.last << a
- end_check()
- self
- end
- def end_check()
- n = @stack.last.nodenum
- if n && n == 0
- end_node()
- end_check() #再帰
- end
- end
- def check_integrity
- n = @stack.last.nodenum
- return nil if @root.length == 0 #no tree is good tree
- return "unmatch leaves" if n && n != 0
- return "extra nodes" if @root.first.is_a?(Node) && @root.length != 1
- return "extra leaves" if @root.length != 1
- return nil
- end
- def nodes
- r = @root.nodes
- r.shift
- r
- end
- def sub_nodes
- r = nodes
- r.shift
- r
- end
- def to_s() @root.to_s end
- def inspect() @root.inspect end
- end
-
- class IDS_Tree < Tree #======================================================================
- def initialize(str)
- @str = str
- super()
- parse()
- end
- def parse()
- @str.each_char {|ch|
- char = Character.new(ch)
- if is_ids?(char)
- add_node(char, ids_operator_argc(char))
- else
- add_leaf(char)
- end
- }
- end
- def is_ids?(obj)
- return true if "+*".include?(obj.to_s) #テスト用ですかね
- return true if obj.is_ids?
- return false
- end
- def ids_operator_argc(obj)
- return obj.ids_operator_argc if 0 < obj.ids_operator_argc
- return 2 #テスト用ってことで
- end
- def check_integrity
- r = super
- return r if r #不完全がすでにわかっているならreturn
- return "contains ques" if @str =~ /\?/ #?が含まれている?
- return nil
- end
-
- end
-
- class IDS #======================================================================IDSそのものを扱うclass
- def initialize(str) #IDS文字列をうけとる。
- @str = str
- end
- def parse
- end
- def parse_x #柔軟型のParse. IDSキャラクターが前にきてなくてもよい。などなど。
- end
- end
-
- class Counter #======================================================================
- #使い方
- #counter = Counter.new(50) { exit }
- #counter.count
- def initialize(max)
- @max = max
- @count = 0
- @proc = proc
- end
- def count
- @count += 1
- if @max <= @count
- @proc.call
- end
- end
- end
-
- class DBS_Management #======================================================================ファイル管理
- OBSOLETE_ATTRIBUTES = "
-cns-radical
-cns-radical?
-kangxi-radical
-daikanwa-radical
-unicode-radical
-
-cns-strokes
-kangxi-strokes
-daikanwa-strokes
-shinjigen-1-radical
-gb-original-radical
-japanese-strokes
-jis-strokes-a
-jis-strokes-b
-jisx0208-strokes
-jis-x0213-strokes
-jisx0213-strokes
-unicode-strokes
-
-totalstrokes
-cns-total-strokes
-jis-total-strokes-b
-
-non-morohashi
-
-=>ucs*
-#=>mojikyo
-#=mojikyo
-->identical
-
-ancient-ideograph-of
-ancient-char-of-shinjigen-1
-original-ideograph-of
-original-char-of-shinjigen-1
-simplified-ideograph-of
-vulgar-ideograph-of
-vulgar-char-of-shinjigen-1
-ideograph=
-ideographic-variants
-variant-of-shinjigen-1
-
-iso-10646-comment
-".split
- def initialize
- @odir = DB_DIR+"/system-char-id/obsolete" #直打ちしている。
- end
- def move_obsolete_files # 廃止予定のbdbファイルをobsoleteディレクトリーにつっこむ
- db = CharDB.instance
- db.close_all
- Dir.mkdir(@odir) unless FileTest.directory? @odir
- OBSOLETE_ATTRIBUTES.each {|attr|
- next if attr =~ /^#/
- filename = db.get_filename(attr)
- move_to_obsolete(filename)
- move_to_obsolete(filename+".txt")
- }
- end
- def move_to_obsolete(file)
- cmd = "mv #{file} #{@odir}"
- # p cmd
- system cmd
- end
- end
-
- class JoyoList #======================================================================
- include Singleton
- #JP_JOYO_FILE = DB_DIR+"/../jp-joyo.txt" #EUC-jisx0213
- JP_JOYO_FILE = DB_DIR+"/../joyo-ucs.txt" #UCS
- COMPOSIT_KANJI = "鳴名加品古知問間聞取兄見切分粉貧林森校東明住位好岩砂里男畑習休短空坂島倉美孝赤看光初努協解新歌語話張強忘悲答晴現正字安守灰秋秒困国医包同合舌居右左受友反道返迷花菜集机主太氷州点店庫仕帳幼防引配早直班筆重番北化比死夏後進酒福私家世内谷半原前寺思電雲気布旅衆泣"
- # COMPOSIT_KANJI = "鳴名加品古"
- def initialize
- @nchars = []
- read_file
- end
- attr_reader :nchars
- def read_file
- open(JP_JOYO_FILE) {|f|
- while line = f.gets
- next if line =~ /^;/ #コメントはとばす
- line.chomp!
- #stroke, nchar, ochar = line.split #new char, old char, old charはnilが多い
- stroke, nchar = line.split
- @nchars << nchar
- end
- }
- end
- def dump_ids(ar)
- ar.each {|ch|
- char = ch.char
- print char.inspect_ids(true), "\t;", char.inspect_ids(false), "\n"
- }
- end
- end
-
end
#----------------------------------------------------------------------終了