日記・コラム・つぶやき

2016年7月19日 (火)

お久しぶりです。

久しぶりの投稿



いろいろあって、かなりの間放置してました。



最近はプログラミングより DTM に時間を費やしています。



Markdown って?



この原稿は iPhone の「Textwell」というアプリで作っています。



このアプリはテキストを打ち込むためのものですが、 Markdown 記法で書いたものを HTML に変換できるので、そのテストを兼ねてます。

2012年7月10日 (火)

最近のこと。

iPhone 用のココログのアプリがひどいという噂だけど、本当のところはどうなんだろう?

試しに自分のブログの記事を書いてみよう。


最近はリア充過ぎて、全然ブログを更新していなかった。

実際のプログラミングはもう何ヶ月もしていない気がする。

それでもボチボチと「すごいHaskell」を読んでたりするんだけどね。

昨日、「素数夜曲」を手に入れたので早く読みたいなぁ…。

でもそのためには、早く「すごいHaskell」を読み終わらないと…。

2012年2月29日 (水)

ブログの内容は鵜呑みにしない方がいいですよ(笑)

どうして中途半端な知識しかもっていない人に限って、ドヤ顔で人にその知識 を教えたがるんだろう?

明らかに Ruby 初心者の人が、解説口調で Ruby のコードの説明をしてるブロ グを見つけたんですけど…説明が微妙に間違ってたり、ブログに書かれてるコー ドが妙に冗長だったり…。

 

例えばこんな感じ…。

 

1000回繰り返したかったら

1000.times do |i|
p i
end

これは1から1000までを単に書き出すプログラムになります。

 

以前このブログでも書きましたが、この場合、"i" には 0 〜 999 の値が入る ので実際は 0 から 999 が書き出されます。

プログラミングの経験がある人ならご存知でしょうが、「0 から始まるか、1 から始まるか」をはっきり認識しておかないと、変なバグに悩まされることが あります。

 

また、フィボナッチ数列を表示し続けるコードが提示してあるのですが、無駄 な処理を含んだ冗長なコードです。

 

フィボナッチの数列は前の2つの項さえ分かっていれば新しい項が生成できるので、 変数を3つ用意します。
そして変数に初期値を入れておきます。

a=1
b=2
c=0

aは第1項目、bは第2項目、cは第3項目です。
そしてloop文を制御するカウンターも必要です。

i=3

3項目から求めるのでカウンターは3からスタートです。
事前準備はこれでおk フィボナッチ数列だけをRubyで書くと

a=1
b=2
c=0
i=3
sum=2
loop do
  if i%3==0 then
    p c=a+b
  end
  if i%3==1 then
    p a=c+b
  end
  if i%3==2 then
    p b=c+a
  end
  i=i+1
end

こんな感じになります。

 

なぜか、数値を格納する変数が3個も準備され、さらに loop文を制御するカウンターまで…。

 

ネットで少し調べれば、このコードよりも効率的なコードはすぐに見つかると 思います。

私なら次のようにしますね。

a = 1
b = 1
loop do
  p a
  a, b = a + b, a
end

 

自分でも同じような間違いを過去に(もしかしたら現在も)犯してるのかな?
ブログはいろいろな人の目に留まるから、気をつけないと…。

もし私のブログの内容に間違いを見つけた人がいらっしゃったら、すぐに教え てください。

また、ブログを読む人は一つのブログの内容を鵜呑みにするのではなく、いく つかのブログを読み比べてみたほうがいいと思います。

なお、この記事は自戒のために書いたので、参考のために挙げたブログへのリ ンクやトラックバックは行なっていません。

HTML generated by org-mode 6.33x in emacs 23

2010年11月 2日 (火)

あなたの「干支」は何ですか?

 いつから「干支(えと)」を聞かれた時に「十二支」だけを答えるようになったんでしょうね。

 そもそも「干支」の漢字の意味は「十干・十二支」のことです。
 「十干」は「甲乙丙丁戊己庚辛壬癸」のことです。「十二支」はご存知の「子丑寅卯辰巳午未申酉戌亥」のことですね。
 さらに「えと」の読み方は「兄弟(えと)」から来ているので、「十干」のことだけを指すはずなのに…。

 ちなみに、なぜ「十干」のことを「兄弟(えと)」と呼ぶかと言うと…
 中国では「五行思想」(木火土金水)に基づいて「十干」を「甲と乙は木、丙と丁は火…」と分類していきました。さらに「甲は木兄(きのえ)、乙は木弟(きのと)、丙は火兄(かのえ)、丁は火弟(かのえ)…」と分けました。この「兄(え)」と「弟(と)」から「兄弟(えと)」になったんですね。

 人に「『えと』は何ですか?」と聞かれた時に、「乙(きのと)です」とか「乙巳(きのとみ)です」と答えたくなるのですが、ぐっと我慢して「巳年です」とだけ答えるようにしています。

2010年4月29日 (木)

人のブログの間違いが気になって……

 基本的に、ほかの人のブログの内容に口を出すのは好きじゃないんですが、どうしても気になることがあるので……。

 

 先日、Ruby に関するこんな記事を見かけました。

Rubyでは、すべてがオブジェクト。じゃないよ!

 この記事を書いた人は、Ruby の根本的なところで勘違いをしているようです。
 ある程度 Ruby や「オブジェクト指向プログラミング」について知識にある人ならすぐに分かる間違いなので、「そのままスルーしてもいいかな?」とも思ったのですが、もし Ruby のことをよく知らない人が読んだら混乱するのではないかと心配になったので、この記事を書くことにしました。

 問題の記事では、冒頭にこんなことが書いてあります。

 Rubyでは、すべてがオブジェクト。と説明される場合があります。確かに、「1」も「+」もクラス自体もすべてオブジェクトです。ですが、「ほぼ」すべてがオブジェクトであって、すべてではないんです。
 例をひとつ。ブロックはオブジェクトではありません。
 確かに Ruby では「すべてがオブジェクトである」と表現されることがあります。しかしこの場合の「すべて」は「すべてのデータ(例えば、文字列、配列など)」という意味になります。
 Ruby には「オブジェクト」以外に「オブジェクト」に属する「メソッド(例えば、 Array#size など)」や「制御構造(例えば、 if や while など)」なども含まれます。そして、一部のメソッド(%, + など)や制御構造(and, or など)は、「演算子」の形をとっています。
 上の文章の例で言えば、「1」はオブジェクトですが、「+」はメソッドです。また「ブロック」は制御構造ということになります。

 さらに記事の最後には

 このように、ブロックはオブジェクトではありません。他にRubyでもオブジェクトでないものに、「and」や「or」、「&&」や「||」などがあります。演算子が特別なのは当たり前だろと思う人は、LISPを調べてみると面白いかもしれません。
といった文章が書いてあります。
 すでに書いたように「ブロック」は制御構造です。「and」、「or」、「&&」、「||」も制御構造です。
 それから、LISP が引き合いに出されていますが、文章の流れからすると「LISP の演算子はすべて手続きである」といったことを表現したかったのでしょうか?
 確かに LISP ほとんどの演算子は手続きといっていいのですが、「and」や「or」など一部の演算子は、引数の評価を通常の手続きと同じようにしてしまうと異常事態に陥る可能性があるため、通常の手続きとは引数の評価のタイミングが違うマクロとして実装されているのが普通です。

 インターネット上のホームページやブログを見ていくと、簡単にいろいろな情報を手に入れることができます。しかし、中には不正確だったり、間違った情報もたくさんあります。
 正しい情報のみをふるい分けるのはなかなか難しいですけどね……。いろいろな記事を見比べたり、人に話を聞いたり、正しい情報を得るにはそれなりに努力が必要ってことでしょうか……。
 かくゆう私のブログの記事も、「思い込み」や「勘違い」で間違った情報を書いている可能性は十分にあります。記事の内容をあんまり鵜呑みにしないほうがいいかも……。

2009年7月 9日 (木)

銀河英雄伝説

最近、「銀河英雄伝説」をまた読み出しました。

「銀英伝」との最初の出会いは高校生のころだったと思います。友人に勧められて読み始めたのでした。

当時は「グイン・サーガ」にはまっていた時期で、「グイン・サーガ」と比べて文章が硬くて密度が濃かったので、結構読むのに苦労した覚えがあります。でもストーリーの面白さや登場人物の魅力に惹かれて、気がつけば本編をすべて読んでいました。

その後、大好きな道原かつみさんが漫画化したものも読みました。おかげで私の頭の中ではヤン、ユリアン、ラインハルト、キルヒアイスなど、主だった登場人物の顔は道原かつみ版の顔以外はありえない状況です。


創元 SF 文庫で復活したのは知っていたのですが、何となく買いそびれていました。でも、やっぱりもう一度読みたくなって、先日買ってしまいました。

自分が年をとったせいか、以前は硬くて読みにくいと思っていた文章も、それほど苦労せずに読めています。

だいたいのストーリーは覚えているつもりなので、今度はじっくりと腰を据えて、細かい内容まで目を通しながら読んでいければと思っています。

ちなみに私の好きな登場人物はヤンとシェーンコップです。自分と一緒でちょっと屈折した人が好きなのかな?

2009年3月29日 (日)

困ったものです --- バグの混入

本当に困ったものです。

本日投稿した記事の中の手続きの一部にバグがあることに気付いちゃいま した。なんで、投稿する前に気付かないんだろう?

とういことで、とり急ぎ記事の訂正をしておきました。具体的には、 「sequence が 3 個の引数を取る場合」にちょっとしたバグが潜んでいまし た。

この手続きを使われる方は新しいバージョン(現在投稿し直された分)を使用 してください。

2009年3月14日 (土)

アルゴリズムの重要性 Project Euler --- Problem 36

Project Euler の問題を解いていると、やっぱり他の人の解き方も見てみたくなりますよね。

そこでネット上にある解答例を探したりするのですが、最近、ちょっと気になることがあります。「取り合えず答えが出ればいい」といった雰囲気のコードが多いのです。

Project Euler に対するスタンスにはいろいろあると思います。

「なるだけ速く、多くの問題を解きたい」というのであれば、アルゴリズムを吟味する意味はあまりないのかもしれません。でも、プログラミングの勉強のために Project Euler の問題を解いているのなら、もう少しアルゴリズムに気を配るべきではないでしょうか?

ひとつの問題を解くためのアルゴリズムはいくつもあります。

中には膨大な計算量が必要となり、メモリや CPU の無駄使いをするものもあるかもしれません。しかし、ちょっと工夫をしたり、アルゴリズムを見直すと、驚くほど計算量を減らせることがあります。

例えば、Problem 36 を考えてみます。

「100 万未満で 10 進でも 2 進でも回文数になるような数の総和を求めよ。」という問題でした。

まず考えつくのが、1 から 999999 までの総ての数に対して条件にあるものを探して行くという方法だと思います。(今回のコードには「リスト内包表記」が含まれています。詳しくは、以前の記事を読んでください)

(define integer->list (lambda (n . radix) (let ([r (if [null? radix] 10 (car radix))]) (do ([n n (quotient n r)] [result '() (cons (remainder n r) result)]) ([< n r] (cons n result)))))) (define palindromic-list? (lambda (lst) (equal? lst (reverse lst)))) (define problem-036 (lambda () (let ([lst (set-of a (a in (cdr (iota 999999))) (odd? a) (palindromic-list? (integer->list a)) (palindromic-list? (integer->list a 2)))]) (printf "~d~%" (apply + lst))))) (time (problem-036))

探す範囲が広いのでかなり時間がかかります。私のパソコンでは "1558 ms elapsed cpu time" と表示されました。

ここでちょっと考え方を変えてみます。まず 10 進法で回文数を作っておいて、その数が 2 進法で回分数になるかを調べてみます。

(define make-palindromic-number (lambda (n . flag) (let* ([a (integer->list n)] [b (reverse a)]) (list->integer (append a (if [null? flag] (cdr b) b)))))) (define problem-036 (lambda () (let* ([base-lst (cdr (iota 999))] [lst-odd (set-of a (b in base-lst) (a is (make-palindromic-number b)) (odd? a) (palindromic-list? (integer->list a 2)))] [lst-even (set-of a (b in base-lst) (a is (make-palindromic-number b #t)) (odd? a) (palindromic-list? (integer->list a 2)))]) (apply + (append lst-odd lst-even))))) (time (problem-036))

この方法では "29 ms elapsed cpu time" となりました。速さにして、約 50 倍です。速さが総てとはいいませんが、アルゴリズムを見直すだけで、こんなに変わってくるものなのです。

使い捨てのスクリプトを作るのなら、あれこれアルゴリズムを吟味する前に、思いつくままにコードを書くほうが結果的に速いかもしれません。しかし、長い間使われ続けるプログラムを作る場合はアルゴリズムを十分吟味するべきだと思います。

最近のソフトは CPU の性能やメモリの量をかなり要求しているものがありますが、しっかりとしたアルゴリズムの検討がなされているのか疑問に思うことがあります。

私はアルゴリズムを考えるのが好きなので、一度解いた問題も、「もっといい方法があるのでは?」と見直し、考え直すことが多いので、なかなか先に進めません。

2008年12月11日 (木)

プログラム言語について語るなら……

 先日、あるブログで「Ruby には goto 文がないので、大域脱出ができずに使いづらい」といった主旨の記事を見ました。→iSAMrx72's思いつきblog
 結論から言うと、Ruby では大域脱出をする場合には "goto" ではなく "catch and throw" を使うので、記事を書いた人が Ruby のことを良く分かっていなかっただけのことでした。

 

 この記事を読んで、いくつか思ったことがありました。

 まず一つは、プログラム言語を批判することについて。
 対象となるプログラム言語を使い込んで、本当に深いところまで知っている人がその言語を批判をしているのは少ない気がします。
 どちらかというと、今回のように本来その言語に標準で備わっている機能を知らずに、「あの機能がない、この関数がない」といった内容の批判が目につくように思います。

 また、自分の得意な言語(使っている言語)の常識を、批判対象となる言語に押し付けて批判をしてしている人も多いように思います。
 それぞれの言語にはそれぞれのプログラムスタイルがあります。その言語に合わないスタイルでプログラムを書けば、プログラムを書きづらいだろうし、速度も上がらないのは当然です。

 「言語には優劣はない。あるのは得意な分野と不得意な分野である」といった内容のことを言っていた人がいます。名言だと思います。
 その言語の不得意とする分野での性能が悪いといって批判するのはある意味卑怯だと思います。

 各言語の理論的な「比較」は、これからプログラム言語を学ぼうとする人にはとても有益だと思います。でも、感情的な「批判」は何の役にも立たちません。

 どのプログラム言語にも長所と短所があります。長所の部分が大好きで、短所の部分に目がつぶれるのであれば、その言語を使えばいいし、短所の部分がどうしても許せなければ、その言語にしがみつかずに、他の言語を使えばいいのではないのでしょうか?
 上司の命令で、自分の嫌いな言語をいやいや使わされている人以外は、嫌いな言語の批判をする暇があったら、自分の大好きな言語で自分や他の人に役に立つプログラムをガンガン作ってもらいたいものです。

 

 もうひとつ気になったのが、「なんで今さら "goto" なのか?」ということです。
 "goto" の乱用の反省から構造化プログラミングは生まれたはず。"goto" を使わなければ困るほど深いネストが出来上がった場合、アルゴリズム自体に問題がある場合がほとんどだと思います。

 私は、N88-BASIC、アセンブラ、C、Ruby、Scheme と使ってきましたが、BASIC とアセンブラはともかく、C や Ruby で "goto" や "catch and throw" を使った記憶がありません。
 私のような趣味でプログラミングをしている者が知らないだけで、もしかしたら業務用のプログラムを作るようなシビアな場面では "goto" はまだまだ必要なのでしょうか?

 別に 「"goto" が諸悪の根源で絶対使ってはいけない」なんてことは思ってもいませんが、"goto" を使いたくなったら、アルゴリズムを見直すべきじゃないでしょうか?

 

 最後にもう一つ。
 この記事を書くきっかけになったブログのコメント蘭に

変数を宣言しないで使うのは、どんなもんなんでしょうね。Rubyは。昔Basicは宣言無で使ってました。ただし、綴り間違いが多いので、Dimとかで宣言したのですが、Rubyも綴り間違いに悩まされるのでないでしょうかね。
というコメントがありました。

 これも、「Ruby のことが分かってないなー」って感じですね。
 そもそも Ruby は「動的言語」ですから、変数と型が無関係なのが「売り」なのです。(それゆえ、「ダックタイピング」なんかもできるわけで……)
 Ruby の場合、クラスの中に小さいメソッドを埋め込んでいくスタイルが主流なので、思い切り離れた場所で初期化した変数を使う場合はほとんどありません。
 多くの場合、エディタの一画面に収まる範囲でしか変数を使用しないので、変数の綴り間違いはあまりないと思います。
 だいたい、変数の綴り間違いは言語のせいではなく、間違いやすい変数名を付けたプログラマーのせいではないでしょうか?

 Ruby は最近注目されているせいか、Ruby 批判も多い気がします。ただし、そのほとんどは勘違いか言いがかりですけど……。
 それに比べて Scheme の場合はあんまり批判をされてませんね。あるのは Common Lisp ファンとの間の Lisp-1, Lisp-2 論争くらいか?さすがに C や Perl と Scheme を直接比べるのは無理がありますよね。(単にマイナーなだけか?)

2008年10月10日 (金)

「語感」って大事ですよね。

最近、ビジネス雑誌で「見える化」という言葉をちょくちょく見かけるようになりました。(私はビジネスマンではないのですが、そういう雑誌を読むのが好きなので……)

ググってみると、語源はトヨタの「カイゼン活動」にあるらしいんだけど……。どうもこの言葉というか、語感に違和感があります。たぶん、訓読みの動詞に「化」をつけているのが原因だと思うのですが……。「可視化」や「視覚化」だったら全然、違和感ないのにね。

言葉を最初に考える人に「語感」に対するセンスがないからこういった言葉ができてしまうんでしょうね。しかも天下のトヨタが発信地となると、ビジネス雑誌の類がホイホイとその言葉をキーワードにした特集なんかを組んだりして……。言葉を作った人はともかく(元々センスがないんだからしょうがない)、雑誌や本の編集者はもう少し日本語を大事にしてもらいたいなぁ……。

同じように違和感を覚えた言葉に「簡単のために」があります。これは主に理工系の書籍に出てくるんですが……。これも、調べてみると "for simplicity" の訳語として出てきたみたいだけど、私は「簡単にするために」のほうが良いと思うのですが……。

より以前の記事一覧

2016年7月
          1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30
31            
フォト

最近のトラックバック

無料ブログはココログ