2007/10/27

近接連星系での最大の質量を持つブラックホール見つかる

太陽質量の15.65(±1.45)倍のブラックホールが近接連星系で発見された。
http://www.nature.com/nature/journal/v449/n7164/full/nature06218.html
これまでに知られている中では最大の質量のもので、
近傍銀河のMessier 33(M33)の連星系M33 X-7に存在している。
連星系を構成するもう一方の星(伴星)の質量は太陽質量の70.0±6.9倍であり、
ブラックホールはこの星の周りを3.45日周期で回っている。
ブラックホールの質量が観測できたのは、この連星系が食連星であったためである。
つまり、連星系が回転している平面をほぼ真横から観測しているということになる。

なお、単に質量の大きいブラックホールであれば他にも存在が予想されており、
例えば、銀河中心に存在していると考えられているものがある。
その質量は太陽質量の10の6乗倍から9乗倍にもなる。

2007/09/05

トランスフォーマー

ハリウッド映画のトランスフォーマーを見てきた。
内容は金のかかったコメディといえそうだ。

CGの出来はなかなかのものだし、
米軍機がいくつもでてくる。F22やAC130などなど。

ただ、ストーリーが軽い。とっても軽い。
そう感じる原因は、おそらくあのちっちゃい
ディセプトロンのロボットだろう。
動きもしゃべり方もどこかでいそうな
ノリの軽いやつだからだ。

というわけで、きれいなCGを見たければ価値があるかも。

2007/07/28

ケロミン

カエルの人形で演奏!
みょーにかわいいし、おもしろそうだが、値段が微妙…
http://www.keromin.com/

2007/07/26

本の出版

本を出版するときって、出版社に企画書を出すところから始まるらしい。
http://itpro.nikkeibp.co.jp/article/Watcher/20070723/278082

IntelがTBBをGPLで配布

Intel Threading Building Blocks がGPL v2で配布。
http://www.threadingbuildingblocks.org/

ライセンスをよくよく見てみると、GPLv2 with the runtime exception
と書いてある。テンプレートやinline展開された部分については、
GPLが伝播しないよということっぽい。

boost licenseのほうが簡単でいいな…

記事
http://itpro.nikkeibp.co.jp/article/NEWS/20070725/278194/?L=rss

2007/07/01

GPL v3 リリース

とりあえず、メモ。
http://www.gnu.org/licenses/gpl.html

特許に関する条項も入っている。

2007/06/29

フリーのXML DB

IBM社製のXMLデータベース「DB2 Express-C 9」が公開されているとのこと。
http://www.ibm.com/db2/express/

記事はここ。
http://itpro.nikkeibp.co.jp/article/COLUMN/20070531/273212/

2007/06/22

flash メモ

flash を作成するソフト「suzuka」を準備する。
http://www.cty-net.ne.jp/~uzgensho/

active scriptを使うなら、
http://www.geocities.jp/myflashsouko/flash/index4.html
が参考になる。

詳細を調べるには
http://livedocs.adobe.com/flash/8_jp/
にあるドキュメントを参考にすればいい。

2007/06/13

デスクトップ冷暖房機!?

Herman Millerの局所冷暖房装置 C2 だそうで。
http://www.itmedia.co.jp/bizid/articles/0706/12/news079.html
<引用>
社内テストでは、C2は周囲の室温が摂氏22.2度の段階からスタートし、
周囲15センチ四方の温度を44.4度まで暖め、17.8度まで冷却できたという。
</引用>

15センチかぁ、微妙だな。
装置の前方1mくらい効果があればよいのだが。

そもそも、暖房はいいとして、冷房の廃熱はいったいどこへ逃がすんだろう?
いまいち機構がわからん。

2007/05/19

逆指値注文の特許

逆指値注文の特許があるとは。

特許第3875206号

それにしても請求項の記述が長いので、文字数を調べてみた。
 請求項1:1338文字
 請求項2:1647文字

がんばったなぁ。

2007/05/15

リースの資産計上

WBSで出ていたが、08年度からリースで借りた設備が資産計上されるのだそうだ。
これじゃあリースのメリットが一つなくなるな。
リース業界も再編らしい。

2007/05/13

erlang その10

続続続ets module
ets:matchの関連関数を使ってみる。

<ets_tut5.erl>

-module(ets_tut5).
-export([test/0]).


test()->
P = ets:new(test1, [bag]),
ets:insert(P, [{a,1,r},{b,2,s},{b,3,u},{b,4,u},{c,5,u}]),
io:format("~p~n", [ets:match_object(P, {'_','$1','$2'})]),
io:format("~p~n", [ets:match_object(P, {'_','_','_'})]),
io:format("~p~n", [ets:match_object(P, {'_','_','u'})]),
ets:delete(P).


結果は次のようになる。
157> c(ets_tut5).
{ok,ets_tut5}
158> ets_tut5:test().
[{c,5,u},{b,2,s},{b,3,u},{b,4,u},{a,1,r}]
[{c,5,u},{b,2,s},{b,3,u},{b,4,u},{a,1,r}]
[{c,5,u},{b,3,u},{b,4,u}]
true

パターンに一致した要素をそのまま取得できていることが確認できる。また、ets:matchで使えた $1 や $2 は _ と同様に解釈されるようである。

次に、match_object(Tab, Pattern, Limit) と match_object(Continuation) を使ってみる。この2つの関数はPatternに一致した要素のうち、Limit個ずつ結果として受け取るために使う。ここでは、Patternに一致した要素を引数で指定した関数で処理する関数を作ってみる。
<ets_tut6>
-module(ets_tut6).
-export([test/0]).


test()->
P = ets:new(test1, [bag]),
ets:insert(P, [{a,1,r},{b,2,s},{b,3,u},{b,4,u},{c,5,u}]),
X = foreach(P, {'b','_','_'},
fun(X)->io:format("~p~n", [X]) end),
ets:delete(P),
X.


foreach(P, Pattern, Fun)->
foreach(ets:match_object(P, Pattern, 1), Fun).


foreach(X, _) when X=='$end_of_table' ->ok;


foreach({Match, Cont}, Fun)->
lists:foreach(Fun, Match),
foreach(ets:match_object(Cont), Fun).


tupleの先頭の要素が b である要素を表示するようにしたので、
199> c(ets_tut6).
{ok,ets_tut6}
200> ets_tut6:test().
{b,4,u}
{b,3,u}
{b,2,s}
ok

という結果が得られる。

2007/05/11

erlang その9

続続ets module

ets:matchを使ってみる。
この関数はパターンに一致したtupleをテーブルから取り出す。
取り出される値はtupleそのものではなく、指定したtupleの要素のリストとなる。
形式的な定義はリファレンスマニュアルをみればわかるので、使用例を示す。
<ets_tut4.erl>

-module(ets_tut4).
-export([test/0]).


test()->
P = ets:new(test1, [bag]),
ets:insert(P, [{a,1,r},{b,2,s},{b,3,u},{b,4,u},{c,5,u}]),
io:format("~p~n", [ets:match(P, {'_','$1','$2'})]),
io:format("~p~n", [ets:match(P, {'_','$2','$1'})]),
io:format("~p~n", [ets:match(P, {a,'$1','_'})]),
io:format("~p~n", [ets:match(P, {b,'_','$1'})]),
io:format("~p~n", [ets:match(P, {'$1','_',u})]),
ets:delete(P).


これを実行すると、
1> c(ets_tut4).
{ok,ets_tut4}
2> ets_tut4:test().
[[5,u],[2,s],[3,u],[4,u],[1,r]]
[[u,5],[s,2],[u,3],[u,4],[r,1]]
[[1]]
[[s],[u],[u]]
[[c],[b],[b]]
true

となる。matchの第1引数はテーブル識別子で第2引数にパターンを指定する。
最初の出力で指定したパターンは
 {'_','$1','$2'}
であるが、これはPに格納されているtupleのうち、全ての要素が任意であることを示す。
つまり、Pに記録されているtupleが全て得られる。'_'はただ任意であることを示す。
一方、'$1'や'$2'は戻り値として得たい要素であることを示している。
'$1'に指定された要素は戻り値のリストの1番目の要素に記録され、'$2'は2番目に記録される。
したがって、得られる結果は
[[5,u],[2,s],[3,u],[4,u],[1,r]]
となる。

2つ目の出力で指定したパターンは最初のものと'$1'と'$2'の位置が入れ替わっている。
これは結果が先ほどのものと順序が逆になるということであり、
[[u,5],[s,2],[u,3],[u,4],[r,1]]
が得られる。

3つ目の出力で指定したパターンは{a,'$1','_'}である。
これはtupleの最初の要素がaであるもののみ取得することを示している。
したがって、最初の要素がaであるのは{a,1,r}であり、出力結果は
2番目の要素で構成されることになっているので、結果は
[[1]]
となる。

4つ目の出力で指定したパターンは{b,'_','$1'}である。
先ほどと同様の理由で、
[[s],[u],[u]]
が得られる。

テーブルのキーでない要素でも指定することができる。
5つ目の出力ではtupleの3番目の要素を指定する。パターンは{'$1','_',u}である。
uに一致するもののうち、最初の要素を集めるので、結果は、
[[c],[b],[b]]
となる。

2007/05/10

erlang その8

続ets module

ets:foldlとets:foldr関数を使ってみる。
lists:foldsとlists:foldrと同様だそうだ。

<ets_tut2.erl>

-module(ets_tut2).
-export([test/0]).


fold(Option)->
P = ets:new(test1,Option),
ets:insert(P,{a}),
ets:insert(P,{b}),
ets:insert(P,{c}),
CL = ets:foldl(fun(X, Con)->[X|Con] end, [{d}], P),
io:format("foldl ~p ~p~n", [Option, CL]),
CR = ets:foldr(fun(X, Con)->[X|Con] end, [{d}], P),
io:format("foldr ~p ~p~n", [Option, CR]),
ets:delete(P).


test()->
fold([]),
fold([ordered_set]).


実行結果は次のようになった。
1> c(ets_tut2).
{ok,ets_tut2}
2> ets_tut2:test().
foldl [] [{c},{b},{a},{d}]
foldr [] [{c},{b},{a},{d}]
foldl [ordered_set] [{c},{b},{a},{d}]
foldr [ordered_set] [{a},{b},{c},{d}]
true

Optionが空、つまりsetの場合は、foldlとfoldrの結果は同じになった。
一方、ordered setの場合は、foldlとfoldrの結果は異なった。

ordered setの場合、foldlは最初の要素から順に関数を実行していくので、
まず初期値[{d}]の前方に{a}が付けられる。したがって、[{a},{d}]となる。
つぎの要素は[{b}]なので、[{b},{a},{d}]となり、最後の要素の処理が終わると、
[{c},{b},{a},{d}]となる。
foldrの場合はその逆に動作するので[{a},{b},{c},{d}]となる。


次に、ets:lookupとets:lookup_elementを使ってみる。
<ets_tut3.erl>
-module(ets_tut3).
-export([test/0]).


test()->
lookup([set]),
lookup([ordered_set]),
lookup([bag]),
lookup([duplicate_bag]).


lookup(Option)->
P = ets:new(test1, Option),
ets:insert(P, [{a,10},{a,20},{a,20},{b,1},{b,5},{b,2}]),
io:format("~p ~p~n", [Option, ets:lookup(P,a)]),
io:format("~p ~p~n", [Option, ets:lookup(P,b)]),
io:format("~p ~p~n", [Option, ets:lookup_element(P,a,2)]),
io:format("~p ~p~n", [Option, ets:lookup_element(P,b,2)]),
ets:delete(P).


実行結果は次のようになった。
1> c(ets_tut3).
{ok,ets_tut3}
2> ets_tut3:test().
[set] [{a,20}]
[set] [{b,2}]
[set] 20
[set] 2
[ordered_set] [{a,20}]
[ordered_set] [{b,2}]
[ordered_set] 20
[ordered_set] 2
[bag] [{a,10},{a,20}]
[bag] [{b,1},{b,5},{b,2}]
[bag] [10,20]
[bag] [1,5,2]
[duplicate_bag] [{a,10},{a,20},{a,20}]
[duplicate_bag] [{b,1},{b,5},{b,2}]
[duplicate_bag] [10,20,20]
[duplicate_bag] [1,5,2]
true

lookupは第2引数で指定したキーに一致する要素一覧を取得する。
setとordered_setの結果は同じ。
bagは同じキーの重複は許されるが、内容が全て同じ要素の重複は許されない。
duplicate_bagはどのようなケースでも重複が許される。
そのため、キーaに対するbagとduplicate_bagの結果が異なっている。

lookup_elementの第3引数にはtupleの何番目の要素を取得するかを指定する。
ここでは2と指定したので、tupleの2番目の要素である数字のリストが得られる。

2007/05/09

erlang その7

ets:new とその関連関数を使ってみる。
これらの関数はテーブルを作成して、そこに色々な要素を記録しておくために使われるようだ。
C++のstd::mapの高機能版のようなものか?

まず、テーブルを作成する。
第1引数はテーブルの名前で、第2引数はオプションを指定する。[]でデフォルトが利用される。
Pにはテーブル識別子(マニュアルではtid()と記載されている)が代入される。
1> P=ets:new(table1,[]).
16

次にこのテーブルの情報を見てみる。
2> ets:info(P).
[{memory,279},
{owner,<0.30.0>},
{name,table1},
{size,0},
{node,nonode@nohost},
{named_table,false},
{type,set},
{keypos,1},
{protection,protected}]

マニュアルによるとmemory は 「The number of words allocated to the table.」
とのことなので、単位をbytesであるとはいえそうにない。
sizeはテーブルに記録されているオブジェクトの数で、今は空なので0になっている。

テーブルに要素を追加してみる。
3> ets:insert(P, {aaa}).
true

テーブルの情報をみると、
4> ets:info(P).
[{memory,289},
{owner,<0.30.0>},
{name,table1},
{size,1},
{node,nonode@nohost},
{named_table,false},
{type,set},
{keypos,1},
{protection,protected}]

となっており、要素数が1増えている。
さらに追加してみると、
5> ets:insert(P, {bbb}).
true
6> ets:info(P).
[{memory,299},
{owner,<0.30.0>},
{name,table1},
{size,2},
{node,nonode@nohost},
{named_table,false},
{type,set},
{keypos,1},
{protection,protected}]

要素数が2になった。また、memoryが10ずつ増えている。
もう少し短いatomを追加してみる。
7> ets:insert(P, {c}).
true
8> ets:info(P).
[{memory,309},
{owner,<0.30.0>},
{name,table1},
{size,3},
{node,nonode@nohost},
{named_table,false},
{type,set},
{keypos,1},
{protection,protected}]

要素数が3になり、memoryは前と同様に10増える。

要素を順番に見ていくには、ets:first/1とets:second/2を使う。
まずets:first/1を使って、
9> ets:first(P).
c

最初の要素はcのようだ。次にets:next/2を使って、
cの要素の次に記録されている要素を順次取得する。
10> ets:next(P,c).
aaa
11> ets:next(P,aaa).
bbb
12> ets:next(P,bbb).
'$end_of_table'

テーブルの最後までくると、'$end_of_table'が返される。
これで終端かどうかが判断できる。

ところで、このテーブルの機能は便利なのだが
テーブルに記録した値は変更できてしまうことになる。
使い方によってはC言語っぽい書き方ができてしまいそうだ。

また、ets.erlによると、これらetsモジュールの関数の一部、
例えばnewやfirst, nextの実装はC言語でされているとのことだ。

2007/05/08

erlang その6

ファイル名に.を含めてみる。
<ets.tut1.erl>

-module(ets.tut1).
-export([test/0]).
test()->io:format("~p~n", ["test"]).

これをコンパイルしてみると、
1> c(ets.tut1).
** Module name ''ets.tut1'' does not match file name ''ets.tut1'' **
{error,badfile}

となる。また試しに ' でくくってみた。
2> c('ets.tut1').
** 2: syntax error before: c **

やはりエラー。
どうやらファイル名を . を含めると正常に処理できないようだ。
リファレンスマニュアルによると
<引用>
The name Module, an atom, should be the same as the file name minus the extension erl.
</引用>
である。また、atomには . を含んでもよい。
このことから、ファイル名の途中に . を含めることができそうにみえるが、できないようだ。
マニュアルのどこかに別途この点について記載がされているのかもしれない…

2007/05/06

erlang その5

●正規表現ライブラリ regexp を使ってみる。

一致した位置を取得する関数 match を使ってみる。
最初の引数が処理対象の文字列で、第2引数が正規表現。
1> regexp:match("a,bc,def,123", ",").
{match,2,1}
結果の2番目が一致した位置で、この場合は最初の,が一致している位置なので、2になる。
0 originではなく、1 originである。
戻り値の最後の値は一致した文字数になので、1になる。

2> regexp:match("a,bc,def,123", ",d").
{match,5,2}
この例では2文字一致しているので戻り値の3番目の値が2になっている。

3> regexp:match("a,bc,def,123", ",d.f").
{match,5,4}
ピリオド.は任意の1文字に一致するので、,defが一致している。

4> regexp:match("a,bc,def,123", ",d.*2").
{match,5,7}
*は0個以上の文字に一致するので、.*で任意の0個以上の文字への一致を調べることになる。
なので、「,def,12」に一致することになり、一致した文字の長さは7文字になる。

マニュアルによるとmatchよりもfirst_matchを使用する方が速いとのこと。
使いかたは同じで、
5> regexp:first_match("a,bc,def,123", ",d.*2").
{match,5,7}

一致する部分を全てみつけたい場合は matches を使う。
6> regexp:matches("a,bc,def,123", ",").
{match,[{2,1},{5,1},{9,1}]}
コンマ,の場所を見付けているので、2文字目、5文字目, 9文字目が見つかる。

今度は、一致した場所の文字を置換する。置換には sub を使う。
この関数では最初に見つけた位置の文字を置き換えるだけ。
7> regexp:sub("a,bc,def,123", ",", " ").
{ok,"a bc,def,123",1}
返される結果の2番目は、置換処理後の文字列となっており、
最初のコンマがスペースに置き換えられている。

一致した場所全てを置き換えたい場合は gsub を使う。
8> regexp:gsub("a,bc,def,123", ",", " ").
{ok,"a bc def 123",3}
結果の3番目の値は置き換えた"箇所"の数で、この例ではコンマが3箇所あるので3になる。

一致した場所で文字列を分割する。これには split を使う。
9> regexp:split("a,bc,def,123", ",").
{ok,["a","bc","def","123"]}
コンマで分割された文字列のリストとして結果が返される。

今回はここまで。

2007/05/03

erlang その4

●ファイル
ファイルの入出力の方法について調べてみた。
まずは、ファイルからの読み込み。
<tut11.erl>

-module(tut11).
-export([read/1]).

read(FileName)->
Handle = file:open(FileName, read),
if element(1,Handle) /= ok -> element(1, Handle);
true -> show_content(element(2,Handle)),
file:close(element(2, Handle))
end.

show_content(Handle)->
Result = io:get_line(Handle, prompt),
if Result == eof -> ok;
true -> io:format("~p~n",[Result]),
show_content(Handle)
end.

さらにテスト用のファイルを作成する。
<test1.txt>
abc
def
123

コンパイルして、
6> c(tut11).
{ok,tut11}

実行すると、
7> tut11:read("test1.txt").
"abc\n"
"def\n"
"123\n"
ok

のような結果が得られる。
io:get_lineでは改行コードは除去されないようだ。

次にファイルへの書き出しを試してみる。
ついでにio:formatの~pと~wと~sの違いを見てみる。
<tut12.erl>
-module(tut12).
-export([write/2]).

write(FileName, Str)->
Handle = file:open(FileName, write),
if element(1,Handle) /= ok -> element(1, Handle);
true -> write_content(element(2,Handle), Str),
file:close(element(2, Handle))
end.

write_content(_, [])->ok;
write_content(Handle, [Head|Rest])->
io:format(Handle, "~p,~w,~s~n", [[Head],[Head],[Head]]),
write_content(Handle, Rest).

コンパイルして、
36> c(tut12).
{ok,tut12}

実行してみる。
41> tut12:write("test2.txt", ["abc"]).
出力されたファイルの内容は、
["abc"],[[97,98,99]],abc

つまり、
~p : 入力された内容をそのまま出力。
~w : 各文字を値として解釈
~s : 文字列として解釈
ということになるようだ。(詳しくはerlangのreference manualを参照のこと)

今度は、日本語に挑戦。
ただ、erlang shellは日本語を受け付けてくれないので、
UTF-8の文字コードを直接入力してみる。

42> tut12:write("test2.txt", [227,129,130]).
出力されたファイルの内容は、
"�",[227],
[129],[129],�
[130],[130],�

ん?各値ごとに出力しようとしているようだ。

["abc"]のようにするには、
46> tut12:write("test2.txt", [[227,129,130]]).
とすればよい。
この出力結果は、
[[227,129,130]],[[227,129,130]],あ

のようになる。~sの出力が日本語になっている。
むろん、UTF-8で日本語が表示できるUNIX shell等で表示させている。

erlang その3

●文字列に関して
Atomは文字で、小文字から始まらないorアルファベットか数字以外の文字で
構成されるときはシングルクォート'で囲まないといけない。

Stringはダブルクォート"で囲まれた文字。
Erlangのデータ型ではなく、Listとして表現される。

●Shellに関して
Shellで定義した変数を消去するには、f()を使うとよい。
1> X=1.
1
2> X=2.

=ERROR REPORT==== 2-May-2007::22:19:18 ===
Error in process <0.30.0> with exit value: {{badmatch,2},[{erl_eval,expr,3}]}

** exited: {{badmatch,2},[{erl_eval,expr,3}]} **
3> f().
ok
4> X=2.
2

さらに特定の変数の定義を除去することもできる。
5> Y=3.
3
6> X=3.

=ERROR REPORT==== 2-May-2007::22:20:08 ===
Error in process <0.33.0> with exit value: {{badmatch,3},[{erl_eval,expr,3}]}

** exited: {{badmatch,3},[{erl_eval,expr,3}]} **
7> Y=2.

=ERROR REPORT==== 2-May-2007::22:20:10 ===
Error in process <0.38.0> with exit value: {{badmatch,2},[{erl_eval,expr,3}]}

** exited: {{badmatch,2},[{erl_eval,expr,3}]} **

この時点で、X=3, Y=2となっている。
8> f(Y).
ok

これでYの定義のみが消去された。なので、
9> X=3.

=ERROR REPORT==== 2-May-2007::22:20:18 ===
Error in process <0.40.0> with exit value: {{badmatch,3},[{erl_eval,expr,3}]}

** exited: {{badmatch,3},[{erl_eval,expr,3}]} **

のように、Xは定義済みなので再定義できないが、Yについては先ほど消去しているので
10> Y=2.
2
のように再定義できる。

●erlangプログラムのコンパイル
いろいろ探してみたが、ネイティブコードを出力するコンパイラを見つけられない…

とりあえず、UNIXのshellから実行できるようにするには、
(1)コマンドラインから.erlファイルを実行
(2).erlプログラムの最後にhalt().を書いて、shellを止める
の2つを行うしかなさそうだ。

あんましよさげではないが、例えば
<tut10.erl>
-module(tut10).
-export([main/1]).
main(X)->io:format("~p~n",[X]),
     halt().

のようなファイルを作成し、
UNIX> erl -compile tut10.erl

としてコンパイルして、
UNIX> erl -noinput -run tut10 main abc
["abc"]

のようにして実行する。ちなみに日本語を入れると、
UNIX> erl -noinput -run tut10 main あ
[[227,129,130]]

となり、日本語の出力ができない。
データの値からしてUTF-8でエンコードされているようだ。
なので、ファイルにバイナリで出力できれば読めそう。

erlang shell や UNIX shell に日本語を出力する方法は見つけられず…