6. 共通パラメータ¶
処理メソッドで指定できるパラメータには、概ね共通した意味で用いられるものが多い。 ただし、メソッドによっては全く異なる意味として実装されているケースもあるので注意されたい。 表 6.1 に一覧を示し、続いてその内容について詳述する。
表 6.1 入力データ例:mcmdが扱う表構造データ¶ キーワード
内容
入力データの指定
出力データの指定
入出力項目名の指定
キー項目名
並べ替え項目名
自動並べ替えの無効化
追加項目名
入出力データの1行目を項目名ヘッダとみなさない
項目名ヘッダを出力しない
項目番号による指定
有効桁数の変更設定
作業ファイル格納パス名
ベクトル型データの区切り文字
キー単位処理のバッファ数
入出力件数が異なればwarningを出す
キー項目のNULL値にwarningを出す
入力項目のNULL値にwarningを出す
出力項目のNULL値にwarningを出す
6.1. i= m= : 入力データの指定¶
入力データを指定するパラメータ( i=
と m=
)には、
CSVファイル名、Pythonリスト、処理フローオブジェクトを指定できる。
中には mnewrand
のように入力データを必要としないメソッドもあるが、
i=
はほとんどのメソッドで利用できるパラメータであり、
m=
は mjoin
など参照データを利用するメソッドにおいて利用される。
いずれの形式であっても、全行で同数の項目数を持っていなければエラーとなる。
i=
が省略された時には標準入力からデータを読み込む。
この機能があるために、パイプラインによる接続が可能となる。
例えば、 リスト 6.1 では、 msum
で i=
を指定していないが、
これは mcut
の結果がパイプラインを介して標準入力としてCSVデータが入力されるためである。
1import nysol.mcmd as nm 2dat=[ 3["customer","date","amount"], 4["A","20180101",5200], 5["B","20180101",800], 6] 7 8f=nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount") 9print(f.run()) 10# [['A', '15600'], ['B', '2400']]
入力データの複数指定¶
入力データを複数指定することもでき、その場合は、それらのデータが全て併合される。
これは、実行時に m2cat
を自動的に付加することによって実現している。
さらに入力側に接続されたメソッドからの標準入力も併合対象になる。
複数指定したいずれのデータも項目名が同一でなければならない。
サンプルコードを リスト 6.2 に示す。
1import nysol.mcmd as nm
2
3dat=[
4["customer","amount"],
5["A",100],
6["B",300],
7]
8
9# datを3つのCSVファイルに出力
10nm.m2cat(i=dat,o="dat1.csv").run()
11nm.m2cat(i=dat,o="dat2.csv").run()
12nm.m2cat(i=dat,o="dat3.csv").run()
13
14# Pythonリストを複数利用する場合の一つの方法は、Python上で統合した上でmcut nfni=Trueを指定して読み込む
15dat1=dat2=dat3=dat[1:] # 項目名ヘッダを省いたPythonリスト
16f=None
17f <<= nm.mcut(f="0:customer,1:amount",i=(dat1+dat2+dat3),nfni=True)
18f <<= nm.msum(k="customer",f="amount")
19print(f.run())
20# [['A', '300'], ['B', '900']]
21
22# CSVファイルを複数指定する例
23f=None
24f <<= nm.mcut(f="customer,amount",i=["dat1.csv","dat2.csv","dat3.csv"])
25f <<= nm.msum(k="customer",f="amount")
26print(f.run())
27# [['A', '300'], ['B', '900']]
28
29# 処理フローオブジェクトを複数指定することも可能(ここでは簡単のため同じデータdatを使っている)
30f1=nm.mcut(f="customer,amount",i=dat)
31f2=nm.mcut(f="customer,amount",i=dat)
32f3=nm.mcut(f="customer,amount",i=dat)
33f=nm.msum(k="customer",f="amount",i=[f1,f2,f3])
34print(f.run())
35# [['A', '300'], ['B', '900']]
36
37# Pythonリスト、CSV、処理フローオブジェクトを混在させることも可能
38f=nm.msum(k="customer",f="amount",i=[dat,f1,"dat1.csv"])
39print(f.run())
40# [['A', '300'], ['B', '900']]
41
42# mcutからの標準入力も併合可能
43f=None
44f=nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount",i=["dat1.csv",dat])
45print(f.run())
46# [['A', '300'], ['B', '900']]
6.2. o= u= : 出力データの指定¶
出力データを指定するパラメータ( o=
と u=
)には、
CSVファイル名、Pythonリストを指定できる。
中には msep
のように o=
を指定しないメソッドもあるが、
o=
はほとんどのメソッドで利用できるパラメータであり、
u=
は mselstr
など行を選択するメソッドにおいて、
条件にアンマッチの行を出力するデータとして用いられる。
o=
が省略された時には標準出力にデータを書き込む。
この機能があるために、パイプラインによる接続が可能となる。
例えば、 リスト 6.3 では、 mcut
で o=
を指定していないが、
これは mcut
の結果がパイプラインを介して標準出力としてCSVデータが msum
に出力されるためである。
1import nysol.mcmd as nm 2dat=[ 3["customer","date","amount"], 4["A","20180101",5200], 5["B","20180101",800], 6] 7 8f=nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount") 9print(f.run()) 10# [['A', '15600'], ['B', '2400']]
リスト 6.4 に利用例をいくつか示す。
CSVファイルに出力するには、 o=
にファイル名を与えればよい。
リストに出力する時は、 o=
に空のリストを与えればよい。
ただし、追記になるので、リストが空でなければ追記されていく。
さらに、項目数などフォーマットが異なっていても追記できるので、扱いには注意が必要である。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","date","amount"], 5["A","20180101",5200], 6["B","20180101",800], 7] 8# o=に空のリストを与えると、そこに結果が出力(追記)される。ただし、項目名は出力されない。 9result=[] 10nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount",o=result).run() 11print(result) 12# [['A', '5200'], ['B', '800']] 13 14# 追記なので、同じことをもう一度すると、上の結果に追記される。 15nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount",o=result).run() 16print(result) 17# [['A', '5200'], ['B', '800'], ['A', '5200'], ['B', '800']] 18 19# さらに、項目数が異なっていても追記してしまうので、扱いには注意が必要である。 20nm.mcut(f="customer,date,amount",i=dat).msum(k="customer",f="amount",o=result).run() 21print(result) 22# [['A', '5200'], ['B', '800'], ['A', '5200'], ['B', '800'], ['A', '20180101', '5200'], ['B', '20180101', '800']] 23 24# o=を省略すると、結果をリストで返す。追記とはならない。 25result=nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount").run() 26print(result) 27# [['A', '5200'], ['B', '800']] 28 29# o=に文字列を与えるとCSVファイル名とみなし、ファイル出力される。項目名も出力される。 30nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount",o="result.csv").run() 31print(result) 32# result.csvの内容 33# customer%0,amount 34# A,5200 35# B,800
6.3. f= : 入出力項目名の指定¶
処理対象となる入力項目名の指定をおこなう。
例えば、mcut においては「選択される項目名」、
magg においては 「集計される項目名」、
mjoin においては「結合される項目名」を指定する。
また複数の項目名は、 f="a,b,c"
のようにカンマで区切って指定する。
さらに、mcut、msum、mjoinのように指定された項目毎に出力項目名を指定できるメソッドもある。
出力項目名は、 f="a:A,b:B"
のように、入力項目名の後にコロンで区切って指定する。
出力項目名が省略されたときは、入力項目名と同じ項目名が利用される。
その利用例を リスト 6.5 に示す。
1import nysol.mcmd as nm 2dat=[ 3["customer","date","amount"], 4["A","20180101",5200], 5["B","20180101",800], 6] 7# msumの集計項目の名称をamountからtotalに変更して実行。 8result=nm.mcut(f="customer,amount",i=dat).msum(k="customer",f="amount:total",o="result.csv").run() 9# result.csvの内容 10# customer%0,total 11# A,5200 12# B,800
6.4. k= : キー項目の指定¶
キー項目を指定する(複数項目指定可)。
キー項目とは、集計の単位として指定したり、またファイルの結合時に2ファイル間の共通項目として指定する項目である。
例えば、msum では、同一キーごとに合計処理をおこなう(集計キーブレイク処理)。
また mjoin では、2 つのデータファイルについて、キー項目の大小を見比べて結合処理を実施する(結合キーブレイク処理)。
k=パラメータが指定されたとき、多くのメソッドでは、その項目を文字列昇順で並べ替えた上で、
それぞれの処理を実行する。
並べ替え処理は、実行時に自動追加される(「 メソッドの自動追加 」節参照)。
ただし、入力データがk=で指定した項目で既に並べ変わっている時は、並べ替えは実行されない(必要ない)。
また、mhashsum メソッドのように、アルゴリズムの性質から k=
を指定しても
並べ替えを行わない例外的なメソッドもある。
なおキーブレイク処理については、 後述 するが、
項目の並べ替えが頻繁に発生するとパフォーマンスの低下を招くため、
キーブレイク処理の内容と必要性を理解した上で、並べ替えの回数を少なくするスクリプトを記述することが望ましい。
リスト 6.6 に集計キーブレイク処理の例としてmsumを、
そして結合キーブレイク処理の例として mjoinの例を示す。
なお、出力されたCSVデータの項目ヘッダの%に続く特殊記号の意味は「 項目名ヘッダー 」の節を参照されたい。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","date","amount"], 5["A","20180101",5200], 6["B","20180101",800] 7] 8 9cust=[ 10["customer","gender","age"], 11["A","female",49], 12["B","male",25] 13] 14 15# 集計キーブレイク処理の例 16# customer別にamountを合計する処理。 17# バックでcustomer項目が並べ替えられてからamount項目の合計処理が行われる。 18nm.msum(k="customer",f="amount",i=dat,o="result.csv").run() 19# customer%0,date,amount 20# A,20180101,5200 21# B,20180101,800 22 23 24# 結合キーブレイク処理の例 25# customer項目をキーにgender,age項目を結合する処理。 26# バックでdatとcustの両データがcustomer項目で並べ替えられてから結合処理が行われる。 27nm.mjoin(k="customer",m=cust,f="gender,age",i=dat,o="result.csv").run() 28# customer%0,date,amount,gender,age 29# A,20180101,5200,female,49 30# B,20180101,800,male,25
キーブレイク処理¶
キーブレイク処理 とは、その項目が並べ換わっていることを前提として、 同一のキー項目値毎に一定の処理を行う処理方式のことを言う。 キーブレイク処理は大きく分けて 2 つの処理に分けられる。 一つは集計のためのキーブレイク処理 (「 集計キーブレイク処理 」と呼ぶ) で、 他方は結合のためのキーブレイク処理 (「 結合キーブレイク処理 」と呼ぶ) である。 mjoin、mcommon のようにメソッド名に「join」もしくは「common」を含むメソッドが結合キーブレイク処理を、 それ以外の k=パラメータを指定できるメソッドの多くは集計キーブレイク処理を行っていると考えてよい。
たとえば集計キーブレイク処理を行う msum メソッドでは、キー項目の値の変化を検知することで、 同一キー毎に合計処理を実行する。 そのためには事前にキー項目で行を並べ替える(文字列昇順)必要があるので、 合計処理を行う前に、並べ替え処理が実行される(自動追加されるのでユーザは並べ替えを気にする必要はない)。
結合キーブレイク処理はもう少し複雑で、たとえば mjoin メソッドは、2 つのデータについて、
キー項目の大小を見比べる。
キー項目が小さいデータは読み進め、キー項目値が同じであれば結合処理を実施する。
この ようにキー項目値の大小比較をしているため、結合のためのキーブレイク処理においては、
事前に 2 つのデータともキー項目で並べ替えられていることが前提となる。
そのため mjoin は、 i=
と m=
で指定されたデータをそれぞれキー項目で並べ替える。
また、mrjoin のような数値範囲による結合キーブレイク処理においては、数値昇順で並べ替えを行う。
キーブレイク処理を伴うメソッドでは、k=で項目を指定するだけで、
裏で並べ替えをの要否を判断し、必要な場合は並べ替えを実行してくれる。
そのため、ユーザは原則としての並べ替えを意識する必要はない。
ただ並べ替え処理が不要になったわけではなく、
各メソッドが内部的に並べ替え処理を行っているという点に注意が必要である。
スクリプトの構成によっては、並 替え処理が頻繁に発生し、パフォーマンス低下の原因となる。
このことを示す例を リスト 6.7 に示している。
この例では、datに2つの表(custとinvoice)を結合し、customer
別に amount
を合計する処理である。
そして、2つのmjoinの順序を入れ替えるだけで、ソートの回数が1回減ることを示している。
1import os 2import nysol.mcmd as nm 3 4dat=[ 5["customer","invoice"], 6["A","01001"], 7["A","01005"], 8["B","01003"], 9["B","01010"] 10] 11 12invoice=[ 13["invoice","amount"], 14["01001",1800], 15["01005",200], 16["01003",100], 17["01010",800] 18] 19 20cust=[ 21["customer","gender","age"], 22["A","female",49], 23["B","male",25] 24] 25 26# この順番で処理すると、裏でソートが3回実行されることになる。 27f=None 28f <<= nm.mjoin(k="customer",m=cust,f="gender,age",i=dat) 29f <<= nm.mjoin(k="invoice",m=invoice,f="amount") 30f <<= nm.msum(k="customer",f="amount",o="result.csv") 31f.run() 32# result.csvの内容 33# customer%0,invoice,gender,age,amount 34# A,01005,female,49,2000 35# B,01010,male,25,900 36 37# mjoinを入れ替えると、msumでcustomer順に並べ替える必要がなくなり、ソートは2回に減る。 38f=None 39f <<= nm.mjoin(k="invoice",m=invoice,f="amount",i=dat) 40f <<= nm.mjoin(k="customer",m=cust,f="gender,age") 41f <<= nm.msum(k="customer",f="amount",o="result.csv") 42f.run() 43# result.csvの内容 44# customer%0,date,amount,gender,age 45# A,20180101,5200,female,49 46# B,20180101,800,male,25
リスト 6.7 の例は、実行順を入れ替えるだけでパフォーマンスを改善できることを示すものである。 処理フロー全体を調べれば、このような改善(最適化)は自動的に行える可能性があるが、 現在のところ実装はされておらず、将来の課題としたい。
6.5. s= : 並べ替え項目の指定¶
maccum などいくつかのメソッドは、行(レコード)の順序が処理結果に影響を与える。 s=パラメータを指定すると、そのメソッドの実行前に指定の項目で行を並べ替え処理を実行する。 項目の並べ替え方法(並び順)は、数値/文字列、昇順/降順の組み合わせで 4 通り指定できる。 指定方法は、項目名 のあと % に続けて n と r を以下の通り組み合わせる。
文字列昇順: s=項目名 (% 指定なし)
文字列逆順: s=項目名%r
数値昇順: s=項目名%n
数値降順: s=項目名%nr
なお、k=とs=の両方を指定した場合は、k=の項目を優先して並べる。 また、並べ替え項目を複数指定することも可能である。 リスト 6.8 にs=の利用例を示している。 なお、出力されたCSVデータの項目ヘッダの%に続く特殊記号の意味は「 項目名ヘッダー 」の節を参照されたい。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","receiptNo","val"], 5["A","1",1], 6["B","2",2], 7["A","10",3], 8["B","9",4] 9] 10 11# receiptNoを文字列昇順に並べて累計を計算する。 12nm.maccum(s="receiptNo",f="val:accum",i=dat,o="result.csv").run() 13# result.csvの内容 14# customer,receiptNo%0,val,accum 15# A,1,1,1 16# A,10,3,4 17# B,2,2,6 18# B,9,4,10 19 20# receiptNoを数値昇順に並べるとaccumの結果も変わってくる。 21nm.maccum(s="receiptNo%n",f="val:accum",i=dat,o="result.csv").run() 22# result.csvの内容 23# customer,receiptNo%0n,val,accum 24# A,1,1,1 25# B,2,2,3 26# B,9,4,7 27# A,10,3,10 28 29# k=も指定すると、その項目(customer)が優先して並べ替えられる。 30nm.maccum(k="customer",s="receiptNo",f="val:accum",i=dat,o="result.csv").run() 31# result.csvの内容 32# customer%0,receiptNo%1,val,accum 33# A,1,1,1 34# A,10,3,4 35# B,2,2,2 36# B,9,4,6
対象メソッド
6.6. q= : 自動並べ替えの無効化¶
k=で指定した項目による自動並べ替えを無効にしたい場合にこのオプションを用いる。
またs=が必要なメソッドでq=を指定するとs=を省略可能となる。
s=を指定したとしてもソートは実行されない。
リスト 6.9 に利用例を示す。
k=で指定された customer
項目の値に変化のあった時に集計(合計)がおこなわれるため、
入力データの1行目、2,3行目、そして4行目の3ブロックが集計単位となる。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","quantity"], 5["A",1], 6["B",2], 7["B",3], 8["A",4] 9] 10 11# q=Trueを指定すると、自動ソーティングは実行されず、入力データの順序でキーブレイク集計(合計)が計算される。 12nm.msum(q=True,k="customer",f="quantity",i=dat,o="result.csv").run() 13# result.csvの内容 14# customer,quantity 15# A,1 16# B,5 17# A,4
6.7. a= : 追加項目の指定¶
新たに項目を追加するようなメソッドにおいて、その項目名を指定する。 多くのメソッドは、追加する項目は一つであるため、ここで指定する項目名も一つであることが多い。 中には、 mcombi や msetstr のように複数の項目を出力するものもあるが、 その際はカンマで区切って複数の項目名を指定する。 リスト 6.10 に利用例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","quantity","amount"], 5["A",1,100], 6["B",2,50], 7["B",3,200], 8["A",4,99] 9] 10 11# quantityとamountを掛け算した結果を total 項目として追加している。 12nm.mcal(c='${quantity}*${amount}',a="total",i=dat,o="result.csv").run() 13# result.csvの内容 14# customer,quantity,amount,total 15# A,1,100,100 16# B,2,50,100 17# B,3,200,600 18# A,4,99,396 19 20# 本日の日付と曜日を全行にセットし、date と dow の2項目を追加出力している。 21nm.msetstr(v="20180913,thursday",a="date,dow",i=dat,o="result.csv").run() 22# result.csvの内容 23# customer,quantity,amount,date,dow 24# A,1,100,20180913,thursday 25# B,2,50,20180913,thursday 26# B,3,200,20180913,thursday 27# A,4,99,20180913,thursday
6.8. nfn= : 1行目を項目名ヘッダとみなさない¶
このオプションを指定すると入力データの 1 行目を項目名行とみなさず、 また出力データにも項目名を出力しない。 主に1行目に項目名がないデータの場合に利用される。 このオプションを指定すると項目指定で項目名は利用できないので項目番号指定をすることになる。 項目番号は 0 から始まる整数で指定することに注意する。 項目番号の指定方法の詳細は「 項目名 」を参照されたい。 また、自動ソートの機能は全く働かなくなるため、 k= や s= を必要とするメソッドの実行においては、 実行前に明示的に msortf でソーティングを実行する必要がある。 自動ソートは、項目名ヘッダにその情報を記録しており、その情報が使えなくなるからである。 よって、k=やs=を必要とするメソッドを明示的にソーティングせずに実行すれば、 q=True を指定して実行した結果と同等になる。 リスト 6.11 に利用例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["A",1,100], 5["B",2,50], 6["B",3,200], 7["A",4,99] 8] 9 10# 入力データに項目名ヘッダのないので、nfn=Trueを指定し、項目を番号で指定している。 11nm.mcut(nfn=True,f="0,2",i=dat).msum(nfn=True,k="0",f="1",o="result.csv").run() 12# result.csvの内容 13# A,100 14# B,250 15# A,99
6.9. nfno= : 項目名ヘッダを出力しない¶
このオプションを指定すると出力データに項目名行を出力しない。
nfn=True とは違い、
i=やm=で指定される入力データは項目名ヘッダを伴うデータであることを前提としており、
f= や k= などによる項目の指定は項目名で行う。
よって、自動ソートも機能する。
ただし、 f=iName:oName
のように出力項目名を指定しても無効になる。
出力を処理メソッドで接続していった場合、それ以降は自動ソートは無効になる。
ちなみに、入力側のみ項目名ヘッダを想定しない nfni=True
は
mcut でのみ利用可能なオプションである。
リスト 6.12 に nfno=True
の利用例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","amount"], 5["A",100], 6["B",50], 7["B",200], 8["A",99] 9] 10 11# 入力項目は名前で指定するが、出力には項目名ヘッダは出力されない。 12nm.msum(nfno=True,k="customer",f="amount",i=dat,o="result.csv").run() 13# A,199 14# B,250
6.10. x= : 項目番号による指定¶
項目名ヘッダを伴う入力データに対して項目番号によって項目を指定したい場合にこのオプションを用いる。 コロンで区切って出力項目名を指定することも可能である。 また項目名ヘッダを伴うために自動ソートも機能する。 リスト 6.13 に利用例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["customer","amount"], 5["A",100], 6["B",50], 7["B",200], 8["A",99] 9] 10 11# 0番目(customer)項目をキーに1番目項目(amount)の合計を計算する。 12nm.msum(x=True,k="0",f="1",i=dat,o="result.csv").run() 13# result.csvの内容 (項目名ヘッダのソーティング情報も正しく出力される) 14# customer%0,amount 15# A,199 16# B,250 17 18# 出力項目名の変更も可能で、集計項目を total に変更している。 19nm.msum(x=True,k="0",f="1:total",i=dat,o="result.csv").run() 20# result.csvの内容 21# customer%0,total 22# A,199 23# B,250
6.11. precision=¶
浮動小数点を扱うメソッド(msumやmavgなど)の内部で、結果をテキストで出力する際に、
C 言語におけるsprintfの書式 "%. 有効桁数
g" を用いている。
この書式は、データの桁数と指定した 有効桁数
によって、
標準標記 (整数部.小数部: ex. 123.456) と、
指数表記 (仮数部 e± 指数部: ex. 1.23456e+02) を切り替える。
切り替えの基準であるが、データを指数表記で表したときに、指数部が指定の有効桁数を超えるか、
もしくは-5 以下の場合 (すなわち、小数点以下に 0 が 4 つ以上続く場合) に指数表記を採用する。
有効桁数
は 1から16 の整数が指定可能で、デフォルトは 10 である。
n < 1 の場合は n = 1 にセットされ、n > 16 の場合は n = 16 にセットされる。
また、環境変数 KG_Precision を設定することでも有効桁数を変更できる。
ただし、環境変数を変更すると、それ 以降に実行するコマンド全てに反映されることに注意する。
リスト 6.14 に利用例を示す。
id=1 は指数表現で 1.2345678e+08 であり、指数部が有効桁数 6 を超えているので指数表記となり、
仮数部の有効桁数が 6 となっている。
id=2 は指数表現で 1.23456789e+03 であり、指数部が有効桁数 7 を超えていないので標準標記 となり、
整数部 + 小数部の桁数が 6 となっている。
id=4 は指数表現で 1.23456789e-04 であり、指数部が-4 未満では ないので標準標記となり、
有効桁数が 6 となっている。
id=5 は指数表現で 1.23456789e-05 であり、指数部が-4 未満 となるため指数表記となり、
仮数部の有効桁数が 6 となっている。
また、環境変数を KG_Precision='2'
で指定して実行した例では、
mcalの出力結果項目でない val
項目も有効桁数が2桁になっている。
これは、Pythonリスト dat
の val
項目の値がPythonの浮動小数点で入力されており、
それをテキストに変換する時にも環境変数の有効桁数の設定が影響するためである。
なお、この変換は、実行時に自動追加される readlist メソッドが行っている。
1import nysol.mcmd as nm 2 3dat=[ 4["id","val"], 5[1,123456789], 6[2,1234.56789], 7[3,0.123456789], 8[4,0.000123456789], 9[5,0.0000123456789] 10] 11 12# val項目の内容を有効桁数6桁で表示する。 13nm.mcal(c="${val}", a="result", precision=6, i=dat, o="result.csv").run() 14# result.csvの内容 15# id,val,result 16# 1,123456789,1.23457e+08 17# 2,1234.56789,1234.57 18# 3,0.123456789,0.123457 19# 4,0.000123456789,0.000123457 20# 5,1.23456789e-05,1.23457e-05 21 22# 環境変数で有効桁数2桁に設定した場合の例。 23os.environ['KG_Precision'] = '2' 24nm.mcal(c="${val}", a="result", i=dat, o="result.csv").run() 25# result.csvの内容 26# id,val,result 27# 1,1.2e+08,1.2e+08 28# 2,1.2e+03,1200 29# 3,0.12,0.12 30# 4,0.00012,0.00012 31# 5,1.2e-05,1.2e-05
6.12. tmpPath=¶
処理メソッドが内部で用いる作業ファイルを格納するディレクトリ名を指定する。
例えば、msortf は巨大なデータについては分割ソートを用いるが、その一時ファイルとして保存される。
それ以外にも、キー項目の単位が大きくなった場合、キーブレイク処理で一時ファイルが用いられることもある。
また、 処理フローが分岐する際に自動挿入される mfifo の内部バッファでも
一時ファイルが用いられることがある。
一時ファイルの出力ディレクトリは、指定がなければデフォルトとして/tmp が用いられる。
一時ファイルを格納するディレクトリは読み書き可能な状態で存在する必要がある。
一時ファイルは、必ず __KGTMP
から始まるファイル名が用いられる。
作業ファイルは、正常に終了すれば (エラー終了も含めて mcmd のコントロール下で正常に終了するという意味)
削除されるが、不測の事態(例えば、バグ終了の場合)には、消されず残る場合がある。
データ量によっては、非常に多くの作業ファイルが生成される可能性があり (100 万ファイル以上!!)、
その場合は、次に一時ファイルを利用する処理メソッドの動作が極端に遅くなる可能性がある(
100万ファイルあるディレクトリを ls
したときの遅さを想像してみればよい)。
現在のところ、これらの不要ファイ ルの自動消去 (ガベージコレクション) の機能は実装しておらず、
定期的に作業パスのファイルを確認しておくべきである。
なお、/tmpディレクトリは、一般的にはosを再起動すればクリアされる。
また、環境変数 KG_Tmp_Path を設定することで、作業ディレクトリを変更できる。 ただし、環境変数を変更すると、それ以降に実行する処理メソッド全てに反映されることに注意する。 リスト 6.15 に利用例を示す。
1import nysol.mcmd as nm 2# カレントパスのtmp以下に一時ファイルが作られる。 3# 処理が正常に終了すれば、全ての一時ファイルは自動的に消去される。 4nm.msum(k="customer",f="amount",i=dat,tmpPath="./tmp").run() 5 6# 同じことは、環境変数を設定することでも可能である。 7os.environ['KG_Tmp_Path'] = './tmp' 8nm.msum(k="customer",f="amount",i=dat).run()
6.13. delim= : ベクトル型データの区切り文字¶
mvcount などの処理メソッドが扱うベクトル型データについて、要素の区切り文字を指定する。 デフォルトは半角スペースである。 CSV の区切り文字であるカンマを指定することもできるが、ベクトルの区切り文字と区別するために ベクトル全体がダブルクオーテーションで囲われる。 リスト 6.16 に利用例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["vec"], 5["b:a:c"], 6["x:p"] 7] 8 9# val項目の内容を有効桁数6桁で表示する。 10nm.mvsort(vf="vec",delim=":",i=dat,o="result.csv").run() 11os.system("cat result.csv") 12# result.csvの内容 13# vec 14# a:b:c 15# p:x 16 17# delim を指定していないので b:a:c や x:p は一つの要素として解釈される。 18nm.mvsort(vf="vec",i=dat,o="rsult.csv").run() 19os.system("cat result.csv") 20# result.csvの内容 21# vec 22# a:b:c 23# p:x 24 25dat=[ 26["vec1","vec2"], 27["a","b"], 28["p","q"] 29] 30# 区切り文字をカンマにした場合は、ベクトル全体がダブルクオーテーションで囲われることで CSV の区切り文字との区別がつけられる。 31nm.mvcat(vf="vec1,vec2", a="vec3", delim=",", i=dat, o="result.csv").run() 32os.system("cat result.csv") 33# vec3 34# "a,b" 35# "p,q"
6.14. bufcount= : キー単位処理のバッファ数¶
mbucket , mnjoin , mshare など、 キーブレイク処理において、データを複数パス走査する必要のあるコマンドにおいて利用する内部バッファの数 (ブロック数) を指定する。 一つのバッファは 4MB で、デフォルトでは 10 ブロック (40MB) である。 データがバッファに収まらない場合は一時ファイルに書き出されるため、 キーのサイズが非常に大きい場合は、メモリに余裕があれば、 このパラメータを調整することで処理速度の向上が期待できる。 リスト 6.17 に利用例を示す。
1import nysol.mcmd as nm 2# 参照ファイルのキーサイズが 80MB(4MB × 20) 以内であれば、一時ファイルは使われない。 3nm.mnjoin(k="id", m=ref, f="name", i=dat, o="result.csv", bufcount=20).run()
6.15. assert_diffSize= : 入出力件数が異なればwarningを出す¶
このパラメータを指定すると、指定した処理メソッドの入力ファイルと出力ファイルの件数の比較を行い、 入力ファイルと出力ファイルの件数 が異なる場合に、「#WARNING# ; the number of lines is different」 というメッセージを表示する。
例えば、mjoin(参照ファイルの項目結合)を利用する際に、
入力ファイルのキー項目(k=パラメータで指定する項目)と
参照ファイルのキー項目(K=パラメータで指定する項目)が
完全に一致しているかどうかを確認したい場合を想定してみよう。
mjoin で 外部結合で NULL 値を出力する n=True
オプションを指定しない場合は、
入力ファイルと参 照ファイルで共通のキー項目のみが結合され、
一致しないキー項目の値は除外される為、入力データと出力データの件数が異なってくる。
その際、 assert_diffSize=True
を指定しておくと、入力ファイルと出力ファイルの件数の比較を行い、
入力ファイルと出力ファイルの件数が異なる場合にwarningを出してくれる。
そのため入力ファイルと参照ファイルのキー項目が完全に一致していないことを確認することができる。
リスト 6.18 にそのような例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["item","date","price"], 5["A","20081201",100], 6["A","20081213",98], 7["B","20081002",400], 8["B","20081209",450], 9["C","20081201",100] 10] 11ref=[ 12["item","cost"], 13["A",50], 14["B",300], 15["E",200] 16] 17 18# datにrefのcost項目を結合する。しかしdatのキーであるCがref側には無いため、出力が1件少なくなりwarningがでる。 19nm.mjoin(assert_diffSize=True,k="item",f="cost",m=ref,i=dat,o="result.csv").run() 20#WARNING# ; the number of lines is different; 2018/09/13 15:57:49 21os.system("cat result.csv") 22# result.csvの内容 23# item%0,date,price,cost 24# A,20081201,100,50 25# A,20081213,98,50 26# B,20081002,400,300 27# B,20081209,450,300
6.16. assert_nullkey= : キー項目のNULL値にwarningを出す¶
このパラメータを指定すると、キー項目 (k=または K=パラメータで指定する項目)にNULL値が 含まれているかどうかのチェックを行い、NULL 値が含まれていた場合に、 「#WARNING# ; exist NULL in key filed」という メッセージを表示する。 リスト 6.19 に例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["item","price"], 5["A",100], 6[None,98], 7["B",400], 8["B",450], 9["C",100] 10] 11 12# 集計キーitemの2行目にnull値があるので、警告を出してくれている。 13nm.msum(assert_nullkey=True,k="item",f="price",i=dat,o="result.csv").run() 14#WARNING# ; exist NULL in key filed; 2018/09/13 16:07:30 15os.system("cat result.csv") 16# result.csvの内容 17# item%0,price 18# ,98 19# A,100 20# B,850 21# C,100
6.17. assert_nullin= : 入力項目のNULL値にwarningを出す¶
このパラメータを指定すると、f=またはvf=で指定された入力項目にNULL値が含まれているかどうかのチェックを行い、 NULL 値が含まれていた場合に、「#WARNING# ; exist NULL in input data」というメッセージを表示する。 f=などのパラメータで指定していない項目にNULL値があっても警告は出さない。 リスト 6.20 に例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["item","price"], 5["A",100], 6["A",None], 7["B",400], 8["B",450], 9["C",100] 10] 11 12# 集計項目priceの2行目にnull値があるので、警告を出してくれている。 13# msumではnull値は無視して合計処理を行うので結果は問題ない。 14nm.msum(assert_nullin=True,k="item",f="price",i=dat,o="result.csv").run() 15#WARNING# ; exist NULL in input data; 2018/09/13 16:12:25 16os.system("cat result.csv") 17# result.csvの内容 18# item%0,price 19# A,100 20# B,850 21# C,100
6.18. assert_nullout= : 出力項目のNULL値にwarningを出す¶
このパラメータを指定すると、出力項目に NULL 値が含まれているかどうかのチェックを行い、 NULL 値が含まれ ていた場合に、「#WARNING# ; exist NULL in output data」というメッセージを表示する。 ただし、計算項目など、入力データがそのまま出力されるものについてはチェックを行わない。 リスト 6.21 に例を示す。
1import nysol.mcmd as nm 2 3dat=[ 4["item","date","quantity"], 5["A","20180801",10], 6["A","20180805",12], 7["B","20180701",3], 8["B","20180822",44], 9["B","20180901",25] 10] 11 12# 集計項目priceの2行目にnull値があるので、警告を出してくれている。 13nm.mslide(assert_nullout=True,k="item",s="date",f="quantity:nextQtty",i=dat,o="result.csv",n=True).run() 14#WARNING# ; exist NULL in output data; 2018/09/13 16:24:16 15os.system("cat result.csv") 16# result.csvの内容 17# item%0,date%1,quantity,nextQtty 18# A,20180801,10,12 19# A,20180805,12, 20# B,20180701,3,44 21# B,20180822,44,25 22# B,20180901,25,