outliner.py
ファイルに出力し、エラー処理の対応を確認します。
先のプログラムで、見出しに対応するテキストファイルが存在しない時に、無限ループに入る不具合を発見しました。
もちろん、修正します。
print 'warning : not found ', k
の箇所です。
以下、最終プログラムです。
------------ outliner.py
# coding:utf-8
# run on python2.7x
import codecs
import sys
import glob
class Context:
def __init__(self, filename):
f = codecs.open(filename, 'r', 'utf-8')
self.lines_ = f.readlines()
f.close()
def dump(self):
for l in self.lines_:
print l
def line(self, n = 0):
if len(self.lines_) <= n:
return None
return self.lines_[n].rstrip()
def headline(self, n):
l = self.line(n)
if l is None:
return None
if len(l) <= 0:
return None
h = l.lstrip()
if h[0] == '[' and h[-1] == ']':
return h[1:-1]
return None
if 1 < len(sys.argv):
contexts = {}
root = Context(sys.argv[1])
stack = [[root.line(), 1]]
o = None
if 2 < len(sys.argv):
o = codecs.open(sys.argv[2], 'w', 'utf-8')
filenames = glob.glob('*.txt')
for filename in filenames:
a = Context(filename)
k = a.line()
if k is None:
pass
elif 0 < len(k):
if k in contexts:
print 'fatal error : duplicate headline ', k, ' in ', filename
sys.exit()
else:
contexts[k] = a
while len(stack):
cur = stack[-1]
k = cur[0]
n = cur[1]
stack[-1][1] += 1
if k in contexts:
h = contexts[k].headline(n)
if h is None:
l = contexts[k].line(n)
if l is None:
stack.pop()
else:
#print l
# cut comment
if 0 < len(l) and l[0] == '#':
continue
if o is None:
print l
else:
o.write(l)
o.write('\n')
else:
#print '[',h,']'
h0 = h.rstrip()
h1 = h0.lstrip()
stack.append([h1, 1])
else:
print 'warning : not found ', k
stack.pop()
if o is None:
pass
else:
o.close()
------------
本プログラムをテキストエディタに取り込み、全角スペース二つをタブ一つに置き換えてください。
置き換えたテキストを、outliner.pyと変更します。
> python outliner.py root.txt out/out.txt
と実行します。
out/out.txtに出力結果を吐き出します。
実行ディレクトリではなく、別ディレクトリに出力してください。
以下は、アウトライン・プロセッサーを検証するためのサンプルテキストです。
------------ root.txt
てすと
# コメントだよ
[ 操縦士訓練学校を受験する ]
[ 初任務 ]
[ 初任務a ]
------------ 001.txt
操縦士訓練学校を受験する
# コメントだよ
主人公は、幼馴染と一緒に操縦士訓練学校を受験する。
試験会場の門で、幼馴染男は百回目の告白をする。
主人公は、友達として好きだよ、返す。
拳を合わせて、二人一緒に、正規操縦士になることを誓う。
筆記試験、健康診断、最後に仮想訓練装置での模擬戦に臨む。
主人公は、OSを再起動し自己診断画面で、隠しコマンドをレバーとボタン操作で入力する。
上上下下右左右左AB
わずか一秒の自己診断画面で入力成功、開発画面に入る。
主人公は、仮想訓練装置のリミッターを解除する。
模擬戦開始、敵が多数現れて、主人公はリミッターを解除する。
異次元の軌道を描いて、敵の一群を撃破しまくる。
ダントツの得点を叩き出し、仮想訓練装置から降りる。
監視員は、その場でシステムの不具合を突いた違法行為とみなし、主人公に失格を宣告する。
------------ 002.txt
初任務
失意の主人公と幼馴染男が生活する孤児院に、試験の結果が届く。
主人公は補欠合格、幼馴染は合格する。
全寮制の操縦士訓練学校に入学する。
[授業]
採掘任務、十名の最後に主人公が選ばれる。
幼馴染と共に出撃する。
小天体を牽引するための杭を打ち込む。
中から敵が現れる。
安住の地を目指して宇宙をゆく人類の敵、微細機械の自立型の集合体。
氷の大地を割って、無数の金属の手が現れる。
訓練生の一人が操縦する機体が直撃をくらう。
主人公が操縦する機体も弾き飛ばされる。
幼馴染は、主人公を守って必死に応戦する。
主人公は心肺停止。
しかし、作業用の型落ち兵器、装備も少ない。
主人公は蘇生、リミッター解除し、敵の群れの突破口をひらく。
幼馴染の機体と共に脱出。
直後に、船から放たれた飛翔体が、小天体に打ち込まれる。
敵は、バラバラになり吹き飛ぶも、核が残ったまま。
再度の襲撃は時間の問題。
------------ 002-a.txt
授業
授業で、この船をとりまく状況を説明する。
主人公は、人がいなくなった真夜中に、リミッター解除して仮想訓練装置で操縦技術を磨く。
主人公と幼馴染の関係を揶揄する、同級生。
訓練生の実力一位の男子、訓練生実力二位の女子とも絡み。
男子は敵対的、女子は無視。
------------
以下は、出力結果です。
階層構造も期待通りに出力されました。
------------ 出力結果
主人公は、幼馴染と一緒に操縦士訓練学校を受験する。
試験会場の門で、幼馴染男は百回目の告白をする。
主人公は、友達として好きだよ、返す。
拳を合わせて、二人一緒に、正規操縦士になることを誓う。
筆記試験、健康診断、最後に仮想訓練装置での模擬戦に臨む。
主人公は、OSを再起動し自己診断画面で、隠しコマンドをレバーとボタン操作で入力する。
上上下下右左右左AB
わずか一秒の自己診断画面で入力成功、開発画面に入る。
主人公は、仮想訓練装置のリミッターを解除する。
模擬戦開始、敵が多数現れて、主人公はリミッターを解除する。
異次元の軌道を描いて、敵の一群を撃破しまくる。
ダントツの得点を叩き出し、仮想訓練装置から降りる。
監視員は、その場でシステムの不具合を突いた違法行為とみなし、主人公に失格を宣告する。
失意の主人公と幼馴染男が生活する孤児院に、試験の結果が届く。
主人公は補欠合格、幼馴染は合格する。
全寮制の操縦士訓練学校に入学する。
授業で、この船をとりまく状況を説明する。
主人公は、人がいなくなった真夜中に、リミッター解除して仮想訓練装置で操縦技術を磨く。
主人公と幼馴染の関係を揶揄する、同級生。
訓練生の実力一位の男子、訓練生実力二位の女子とも絡み。
男子は敵対的、女子は無視。
採掘任務、十名の最後に主人公が選ばれる。
幼馴染と共に出撃する。
小天体を牽引するための杭を打ち込む。
中から敵が現れる。
安住の地を目指して宇宙をゆく人類の敵、微細機械の自立型の集合体。
氷の大地を割って、無数の金属の手が現れる。
訓練生の一人が操縦する機体が直撃をくらう。
主人公が操縦する機体も弾き飛ばされる。
幼馴染は、主人公を守って必死に応戦する。
主人公は心肺停止。
しかし、作業用の型落ち兵器、装備も少ない。
主人公は蘇生、リミッター解除し、敵の群れの突破口をひらく。
幼馴染の機体と共に脱出。
直後に、船から放たれた飛翔体が、小天体に打ち込まれる。
敵は、バラバラになり吹き飛ぶも、核が残ったまま。
再度の襲撃は時間の問題。
新規登録で充実の読書を
- マイページ
- 読書の状況から作品を自動で分類して簡単に管理できる
- 小説の未読話数がひと目でわかり前回の続きから読める
- フォローしたユーザーの活動を追える
- 通知
- 小説の更新や作者の新作の情報を受け取れる
- 閲覧履歴
- 以前読んだ小説が一覧で見つけやすい
アカウントをお持ちの方はログイン
ビューワー設定
文字サイズ
背景色
フォント
組み方向
機能をオンにすると、画面の下部をタップする度に自動的にスクロールして読み進められます。
応援すると応援コメントも書けます