2009年11月30日月曜日

Word で他の文書のスタイルをインポートする

1. スタイルの設定

文書を作るときに、予めメニューより「書式 > スタイルと書式」で 見出し のスタイルを設定した。

091130-008.png

上記で設定したスタイルを、新しく作成した文書にインポートしたい。

 

2. スタイルのインポート

メニューより「ツール > テンプレートとアドイン」を選択。

091130-004.png

ダイアログが表示されたら、「構成内容変更」ボタンを押す。

091130-012.png

ダイアログが表示されたら、一度、コピー元とコピー先のファイルを閉じる。

091130-006.png

次に、コピー元を開き、それからコピー先を開く

ファイルを選択するダイアログでは、デフォルトではテンプレートファイルが対象となる。そのため、すべてのファイルが表示されるようにしてから、目的のファイルを選択。

コピー元のインポートしたいスタイルを選択したら、「コピー」ボタンを押す。

091130-013.png

 

関連記事

参考サイト

Skype チャットの読み上げ - 棒読みちゃん

1. 画面が狭いと、チャットウィンドウを見ていられない

自分の PC は画面が狭い。そのため、複数のアプリを起動しながら、Skype のチャットをすることが難しい。

会話の流れがわかるように、チャットウィンドウの内容を読み上げてくれるソフトはないだろうか?

 

2. 聞き取りやすい合成された音声

ニコニコ生放送車載放送 の中で、コメントが自動に読み上げられるのを見たことがある。昔と違って、コンピュータの合成する音声が聞きとりやすくなったことに関心した。

何のソフトを使っているのかと調べてみたら、

というものらしい。

早速ダウンロードして起動。

 

Skype を読み上げるための設定

「その他 > プラグイン」の Skype 読み上げ にチェックを入れる。

※ 初回の起動では、Skype 側で許可する必要あり。

091130-017.png

読み上げを一時停止したい場合は、音声合成タブの Skype のアイコンをクリック。

091130-016.png

このソフト Twitter も読み上げてくれるのでおもしろい。

2009年11月23日月曜日

PDF-XChange Viewer でコメントするときの 識別情報 (名前) を変更する

091123-003.pngPDF で作成された文書に対して注釈を付けたい場合、PDF-XChange Viewer を使う。

このツールでコメントを付けたり、図形や矢印などのマークアップツールを使うと、デフォルトでは Windows にログインしたときのログイン名が表示される。これを変更したい。

 

方法

特定のコメントのみ変更したい場合、コメントを右クリック > 「プロパティ > 一般」の「作者」を変更する。この場合、新しくコメントを作ると前の変更は反映されない。あくまでも変更した対象が変わるだけ。

 

永続的に変更したいときは、メニューより、「編集 > 環境設定」を選択。

環境設定ダイアログの「識別情報」の「ログイン名」は固定されているので、「名前」の方に変更したい名前を入力して、OK ボタンを押す。

091123-002.png

これにより、新しく作るコメントは上記で設定された名前となる。

携帯から写真を Pixelpipe 経由で Twitpic へ投稿 - なるべく小さく安く

1. brizzly で Twitter を閲覧すると画像を見るのが楽しい

最近、Twitter を見るときブラウザは Google Chrome 、クライアント (?) は Brizzly 。補助として pbtweet+ を利用。

Brizzly はフォローしている人のつぶやき全体を眺めるときに使う。チャットのように表示してくれる pbtweet+ は、リアルの友人をリストにまとめて見るときに利用。

Brizzly の良い点は画像へのリンクをインラインに展開して表示してくれるところ。しかも表示のスピードが早い。twitter を眺めるのが、雑誌を読むときのような感覚に近くなる。

 

2. 画像は Twitpic へ投稿

Twitter と連携する画像投稿サービスは百花繚乱。その中でよく見かけるのが Twitpic 。他の画像投稿サイトは「いかに Twitpic を追撃するか」という記事を見かけるところからして、ここが老舗のようだ。寄らば大樹の陰的な発想は好きではないのだけれど、その筋に疎いので、とりあえず Twitpic を利用することに。

Twitpic は Twitter のアカウントを利用してログイン。さすがに海外のサイトなので英語が基本。しかし画像の投稿はシンプルなので問題なし。アップロードと共に Twitter につぶやけるところもいい。 ^^

091123-004.png

しかし、Twitter の機動性の高さが発揮されるべき携帯との連携が、日本語の場合問題となる。 (+_+) 携帯で写真を写しメールに添付して、Twitpic の Settings に書かれているメールアドレスに、日本語を付けて投稿すると文字化けしてしまう。

091123-005.png

追記 (2009.11.29) : iPhone なら Twixy が文字化けもなくお手軽みたい。

 

3. Pixcelpipe から Twitpic へ投稿

文字化けせずに Twitpic に投稿できないものかと調べていたら、

… そんな人はPixelpipeに登録するといいです

(□ 前 の め り □ » Twitpicと日本語と文字化け…そしてPixelpipe より)

聞いたことのないサービスだなぁ。。(@_@;) Yahoo Pipes の親戚かと思ったけれど全然違うみたい。

WEBマーケティング ブログ によると、

これは複数サービスに画像アルバムや動画チャンネルを持っている人にはなかなか便利なサービス。 画像か動画かを自動的に判別し、対応する複数のサービスへ一括でアップロードしてくれます。

(FlickrやPicasa、YouTubeなどに一気に動画や画像をアップできる「Pixelpipe」 より)

つまり、Pixelpipe 自体は色々なサービスへの投稿を楽にするのが目的だけれど、これを経由して Twitpic へ投稿すると、なぜか日本語の文字化けが解消されるということかな。

 

4. 写真のサイズが小さいと Pixcelpipe へ投稿できない

早速、Pixelpipe に登録して、上記の説明を読みながら Twitpic を投稿先として設定。Manage Personal Settings に書かれているアドレスへ写メールで投稿。

091123-001.png

しかし、なぜか投稿されなかった。 (+_+) 

aaaa画像が上手くアップロードできないと Pixelpipe のホームに吹き出しの画像が代わりに表示される。

このとき投稿した写真のサイズは 120 × 1603KB (画質: ノーマル) 。携帯でネットは使わず、パケ放題を利用してないので、なるべく小さい画像で試したかった。ちなみに、自分の携帯の写真の画素数は 130万画素が最高。よく見たら携帯の機種の前に vodafone って書いてある。(@_@;) なめんな、携帯旧世代というスペック ^^;

次に、サイズを 240 × 320 (画質: ノーマル) にして投稿したら今度は上手くいった。120 × 160 では画質を ファイン にしてもダメだった。

 

5. Twitpic へ投稿するには メールのタイトルか本文につぶやきを書く

つぶやく内容を、写メールの タイトル と 本文 に付けた場合、投稿された内容がどうなるか試してみた。

  タイトル 本文
1 通目 [なし] テスト
2 通目 テストタイトル テストだよタイトル

Twitpic の場合、下の方が 1通目になる。

091122-002.png

結局、タイトルか本文のどちらかに つぶやき を付ければ良いようだ。ただし、両方つけたらタイトルが優先される。

 

Flickr の場合 タイトルと本文が反映される

ついでに Flickr への投稿も試した。(右側が 1 通目)

091122-003.png

こちらは本文とタイトルを入力しても、それぞれ反映される。

 

6. 画像サイズと料金の確認

先ほど述べたように、携帯旧世代なのでパケット代が気になる。ちゃんと投稿できたときは 13 KB 。これがいくらになるのか?

自分の場合、softbank のホワイトプランでパケ放題には入ってないので、以下の料金。

パケットって何!?計算方法は!? - ソフトバンクモバイル情報サイト 〓SoftBank Mobile - 楽天ブログ(Blog) によると、

1パケットは、128バイトであります。
1KBは、1024バイト(1MBは1024×1024=1048576バイト)でありますので、パケットで計算しなおすと、1KBは、1024バイト÷128バイトで、8パケットということになると考えられます。

だから、約 13 KB × 8 × 0.21 = 21.84 円。

念のため Web版 パケット計算 で計算を確認してもその通りだった。

塵も積もれば山となる。気をつけよう~。

2009年11月17日火曜日

Google Chrome で HootSuite のフォントサイズを少し大きくしたい

user script のインストール

http://userstyles.org/styles/22613 の Load as user script ボタンを押してインストール。

 

HootSuite の文字が小さくて読みにくい

愛用していた pbtweet が twitter の仕様の変更のためなのか、表示が上手くされないときがあった。pbtweet 以外の twitter クライアントを色々と検討したけれど、やはり pbtweet の会話調の吹き出しに敵うものなし。敢えて別のものを使うとしたら、HootSuite 。しかし、デフォルトでは文字が小さいので読みずらい。 (+_+)

Firefox なら Stylish を使って、

.tweetContent {
    font-size:100% !important;
}

と書けば問題ない。

Chrome でも Stylish のようなものがあるのかな?と思い探したけれどわからなかった。

 

User Script

今、Chrome は開発版を使っている。 どのバージョンからか知らないけれど、XXXXX.user.js という名前のユーザスクリプトファイルを Chrome に D&D してやると簡単にインストールできる。(削除するときは、Google Chrome の設定 > 拡張機能 を開く)

Google Chrome Converts User Scripts into Extensions によると、

Now you can visit userscripts.org and any other site that links to Greasemonkey scripts and other flavors of user scripts, click on the link to a *.user.js file and install it in one click.

ということで、userscripts を書くことに。

userstyles.org のサンプルを見て、必要であろうところのみ抽出。JavaScript で head 要素に style タグを追加するだけ。

// ==UserScript==
// @name           set hootsuite fontsize
// @description    hootsuite 
// @namespace      http://jutememo.blogspot.com
// @include        http://hootsuite.com/dashboard* 
// ==/UserScript==
(function(){
    var fontsize = "100%";
    
    var css = ".tweetContent{font-size:" + fontsize + " !important;}";
    var style = document.createElement('style');
    style.type = "text/css";
    style.appendChild(document.createTextNode(css));
    document.getElementsByTagName("head")[0].appendChild(style);
})();

 

userstyles.org を利用

当初これをエディタに書いて、Chrome に D&D していた。しかし、userstyles.org でアカウントを取得してみたら、CSS を入力するだけで、後は全部自動で上記のようなコードを生成してくれた。userstyles.org のコードはよく使わせてもらっていたけれど、こんなにお手軽に user script を作れるとは今まで知らなかった。 (@_@;)

これなら表示をカスタマイズしたいサイトがあったら、

  1. userstyles.org で CSS を入力
  2. user script を生成
  3. Chrome へインストール

で簡単にできる。 ^^

http://userstyles.org/styles/new

New style | userstyles.org via kwout

2009年11月12日木曜日

Haskell の State モナド (2) - 「状態を変更する関数」を `つなげる関数' を共通部品として括り出す

Haskell の State モナド (1) - 状態を模倣する の続き。

… しかし、前回の内容忘れてもうた。。

パタッ(o_ _)o~†

 

復習

前回は、スタックの内容を変更する pop, push などを連続して適用するために、状態を変更する関数と関数を つなげる comb 関数を定義した。(Control.Monad.State は使わずに。)

ポイントは、最初に、

関数と関数を「つなげる関数」を意識する。

090923-002

そのためには、

関数を「適用する値」と、「適用する関数」に分割して考える

例えば、次のような apply 関数を定義したら、

apply a f = f a

直接、関数 (演算子) に適用する方法と、意識的に分割して適用する方法があることを認識しておく。

*Main> 100 + 1
101
*Main> apply 100 (+ 1)
101

091011-003

手段としては、

    1. 無名関数クロージャで 内側へ内側へ…と計算をつなげ、
    2. 一番内側の関数で自由変数の値を使って計算を組立てる

例えば、3 つの引数を足し合わせる関数 add3 の定義は、

add3 x y z = x + y + z

これを次のように無名関数とクロージャで書くことができる。

add3 = \x -> \y -> \z -> x + y + z

無名関数とクロージャで書かれていたら、省略されている括弧を頭の中で補完。束縛関係を明確に意識する。

add3 = \x -> (\y -> (\z -> x + y + z))

091112-008.png

先ほどの apply 関数と、無名関数・クロージャを使えば、100 + 200 + 300 を次のように書くことができる。

*Main> 100 `apply` (\x -> 200 `apply` (\y -> 300 `apply` (\z -> x + y + z)))
600

これが関数を「つなげる」ことの原型となる。

後は … 端折って、「型に注意しましょう」ということで。 ^^;

 


B0012ORJAM

カウンタの例

前回と同じように、今回は「数を数えるための カウンタ」を操作する関数を「つなげる」ことを考える。

最初に、カウンタの「値」と「増分」をフィールドに持つ Counter a 型を定義。

data Counter a = Counter { val       -- 値
                         , step :: a -- 増分
                         } deriving Show

 

状態を変更する関数

次に、カウンタの値を増分だけ増やす next 関数を定義する。このとき、後で関数をつなげることができるように、前回のスタックの pop 関数のように

pop :: Stack a –> (b, Stack a)

の形に沿った関数の型にする。

next :: Num a => Counter a -> (a, Counter a)
next (Counter v s) = let v' = v + s
                     in (v', Counter v' s)

ここでは返されるタプルの第1要素は、next が適用された後のカウンタの「値」としておいた。

例えば、値 0、増分 1 のカウンタに対して next 関数を適用すると、

*Counter> next (Counter 0 1)
(1,Counter {val = 1, step = 1})

 

「状態を変更する関数」に別名を付ける

前回と同じように next 関数を つなげる 関数を考える。まずは、関数の型が長いと読みにくいので、カウンタを操作する関数の型を「カウンタ操作型」として別名を付ける。

type CounterOp a b = Counter a -> (b, Counter a)

ここで注意することは 型変数 a, b 。上記の next 関数では、たまたまタプルの第1要素がカウンタの値と同じ型だった。しかし、カウンタを操作する関数を他に定義した場合、別の型にしたいこともあるかもしれない。カウンタで使われる値の型の方は、当然ながらカウンタ操作する前と後では変わらない。

 

「状態を変更する関数」を つなぐ 関数

次に上記のカウンタ操作型を つなげる 関数を定義。なぜこのように定義するかは前回を参照。今回は一気に端折って、

comb :: CounterOp a b -> (b -> CounterOp a c ) -> CounterOp a c
comb m n = \counter0 -> let (val1, counter1) = m counter0
                            (val2, counter2) = n val1 counter1
                        in  (val2, counter2)

comb 関数の第2引数が、第1引数に対して全く関心がない場合のために comb_ 関数を定義しておく。

comb_ :: CounterOp a b -> CounterOp a c -> CounterOp a c
comb_ m n = m `comb` \_ -> n

 

ここでカウンタを連続して 3 回カウントさせる next3 関数を上記の comb_ 関数を使って定義してみる。

next3 = next `comb_` next `comb_` next

これを先ほどと同じカウンタに適用すると、

*Counter> next3 $ Counter 0 1
(3,Counter {val = 3, step = 1})

 

ついでなので、next を 3 回つなげて、カウンタの値を足し合わせる関数を定義してみる。

… と、その前に前回と同じように、ある値に適用すると CounterOp a b 型の値を返す関数 ret を定義しておく。ただし、ret 関数では counter の更新は行わない。単に b 型の値を CounterOp a で包むだけ。

ret :: b -> CounterOp a b
ret x = \counter -> (x, counter)

これを元に、

next3' = next `comb` \x1 ->
         next `comb` \x2 ->
         next `comb` \x3 ->
         ret $ x1+x2+x3

早速使ってみる。

*Counter> next3' $ Counter 0 2
(12,Counter {val = 6, step = 2})

 

ここまでのコード

 

スタック操作型 と カウンタ操作型 の比較

ところで、前回のスタックを操作するときに定義 した「スタック操作型」は、次の通りだった。

type StackOp a b = Stack a -> (b, Stack a)

これに対して、今回の「カウンタ操作型」は、

type CounterOp a b = Counter a -> (b, Counter a)

違いは「別名」と、そこで「状態を変更する対象」である具体的な型コンストラクタ

 

comb 関数も同様に見てみると、「スタック操作」版は、

comb :: StackOp a b -> (b -> StackOp a c) -> StackOp a c
comb m n = \stack0 ->
           let (x1, stack1) = m stack0
               (x2, stack2) = n x1 stack1
           in  (x2, stack2)

「カウンタ操作」の comb 関数は、

comb :: CounterOp a b -> (b -> CounterOp a c ) -> CounterOp a c
comb m n = \counter0 -> let (val1, counter1) = m counter0
                            (val2, counter2) = n val1 counter1
                        in  (val2, counter2)

 

ret 関数も同じく「スタック操作」版は、

ret :: b -> StackOp a b
ret x = \stack -> (x, stack)

「カウンタ操作」版は、

ret :: b -> CounterOp a b
ret x = \counter -> (x, counter)

 

「もう、これは共通部分をまとめるしかない」という雰囲気になった。 ^^;

 

State s a 型 (状態 操作型) にまとめる

最初に別名から考える。「スタック操作型」と「カウンタ操作型」を総称する名前にしたいので、「状態操作型」という意味で State s a 型という名前にした。(もちろん、Control.Monad.State.LazyState を真似て…)

type State s a = s -> (a, s)

先ほど具体的な型が書かれていた StackOp, CounterOp の部分を型変数 s とした。 いきなりこの定義を見たら、抽象的な関数で具体的なイメージがわかない。しかし、これに対応した具体的な関数を連想できるので、State s a 型は 状態を変更する関数を表現したものだと解釈できる。

 

これに伴い、同じように comb 関数も具体的な型名を型変数で置き換える。

comb :: State s a -> (a -> State s b) -> State s b
comb m n = \s0 -> let (x1, s1) = m s0
                      (x2, s2) = n x1 s1
                  in  (x2, s2)

ret 関数も同じく、

ret :: a -> State s a
ret x = \s -> (x, s)

 

ここまでのコード

… しかし、これだけ見たら、本当わからんなぁ。。 (+_+)

とにかく、これで スタックを操作していたモジュールと、Counter モジュールに記述していた comb, comb_, ret 関数を削除し、上記の State をインポートすればよくなった。

counter.hs

stack.hs

main.hs

main.hs の main を実行した結果は、

*Main> main
(3,Counter {val = 3, step = 1})
((),Stack [300,200,100,5,4,3,2,1])

Inkscape で取り込んだ画像が表示されない

Inkscape に D&D で画像を取り込んだ。

091112-002.png
画像の元ファイルを移動したら、画像が表示されなくなってしまった。 (+_+) 代わりに `Linked Image not found’ と表示された。(最初、Inkscape のファイル自体を移動させたのが原因かと思っていたら、画像ファイルの方だった。)
091112-004.png

対処

Inkscape@JP - FAQ (Inkscapeの使い方) によると、
画像を埋め込む方法。メニューの「エフェクト」→「画像」→「全ての画像を埋め込む」を実行します。
なるほど。
091112-005.png

ダイアログが表示されるので、Apply ボタンを押す。
091112-007.png

これでファイルをどこへ持っていっても問題なし。 ^^


ファイルサイズの変化
取り込んだ画像のサイズは 98.1 KB (100,470 バイト) 。元の Inkscape ファイルのサイズから画像埋め込み後の変化は次のようだった。
2.50 KB (2,570 バイト) → 134 KB (138,146 バイト)

2009年11月11日水曜日

Google Docs で 段組

追記 (2010.6.16) : 段組のドキュメントをテンプレートギャラリーに追加した。

訂正 (2010.6.18) : 上記の段組は文字を入力している途中で段組が崩れてしまうことがあるので、表による段組も作成。

 

 

HTML の編集

メニューより 「編集 > HTML を編集」

091111-009.png

以下を貼り付けて、「アップデート」ボタンを押す。

<div id="menu">
メニュー
</div>

<div id="content">
内容
</div>
091111-006.png

 

CSS の編集

メニューより 「編集 > CSS を編集」

091111-010.png

以下を貼り付けて、「OK」ボタンを押す。

#menu {
  float: left;
  width: 25%;
}
#content {
  float: left;
  width: 75%;
}

width で幅を指定。上記は比率で指定場合。

091111-011.png

 

これで以下のように表示される。

091111-016.png

 

改行について

Google Chrome

Shift + Enter で、段組の中で改行がされるようだ。Enter キーだけでは、段組が崩れる。

 

Firefox

Enter で改行される。

 

IE8

意外なことに、段組の操作に関しては IE8 が扱いやすい。

適当に入力した文字の辺りをクリックすると、ハンドルが表示される。これで枠の大きさを調整もできる。

091111-013.png

 

ダブルクリックすると文字の入力ができるようになる。枠が表示されたままなので、入力に戸惑うことがない。

091111-015.png

 

参考

2009年11月9日月曜日

Meadow で自動保存をやめる

Meadow でファイルを編集していると、自動的に `ファイル名~’ が作成される。あまりもこのファイルが散らかってきたので、この際自動保存をやめることにした。

バックアップファイルについての設定 によると、

この設定をオフにしてバックアップファイルをつくらせないようにするには, make-backup-filesnilにしておきます.

これを参考に ~/.eamcs に以下のように記述。

(setq make-backup-files nil)

M-x load-file で ~/.emacs をロードしなおす。

 

Emacsでファイルの自動保存 (auto-save-buffers) には、

僕は 以前 からファイルを自動で保存するように Emacs の設定を行っている。…

… キー操作が 0.5 秒ないときに更新の あったファイルがすべて自動的に保存されるようになる。この設定 を行ってから 2年以上の間、C-x C-s をまったく打たなくなった。

と書かれていたけれど、これはまたの機会に試してみよう。

 

ubulog: Emacsの保存関係の設定 には、

… バックアップファイルは専用ディレクトリを作ってそこに全部保存されるようにします。

という設定が書かれていたので、こちらの方が良かったかなぁ。

 

参考

2009年11月8日日曜日

Haskell の Maybe a 型と Either a b 型 (2) - 類似性と違い

Haskell の Maybe a 型と Either a b 型 (1) の続き。

 

Maybe a 型と Either a b 型の類似性

Maybe a 型のコンストラクタは、

Nothing

Just a

この型の意味は 前回 見たように「何もないよの `Nothing’」 と「何かあったよ `Just a’」 で、関数によって取り出したい値が ある場合 と ない場合 を総称した概念を表現している。例えば、何かを検索するための関数の場合、値を見つけたときに Just で包み、見つからなかったら Nothing を返す。他の言語で null や None を返すような曖昧なことをするのではなく、「あった場合、なかった場合」を一つの型としてコンパイラがキッチリとチェックする。

 

この Maybe a 型と似ているのが Either a b 型。

either の言葉としての日常的な使い方は、

Either you or she is to go.
君か彼女かどちらかが行かねばならない

(Yahoo!辞書 – either より)

文字通り「どちらか一方」を表わす型。

どちらか一方」という意味では、Maybe a 型の Nothing と Just も「あるかないか」のどちらか一方を返す関数で使われる。

 

Either a b 型のコンストラクタを見ると、Maybe によく似ている。

Left a

Right b

Maybe と対応させて解釈すると都合がいい。

091028-007

ただし、各々を対応させたのは便宜的なもので、関数を適用した結果、二つの内どちらかに分類することがその本質。違いは、Maybe a 型が Nothing を返したら「もう後はおらぁ知らねぇ~」なのに対して、対応する Either a b 型は律儀にも Left で値を包んで返してくれる。

 

Maybe a 型と Either a b 型の違い

Maybe a 型の例

例えば、次のような状況を想定。

「合格ラインが 80 点のテスト」がある。受験生は合格ラインの得点を知らない。

これに対して、合否を判定する test 関数を定義し、 Maybe a 型を利用してみる。合格なら Just、不合格なら Nothing を返すとする。

goukaku = 80

test score = if score >= goukaku 
             then Just "Goukaku!"
             else Nothing

例えば、このテストで 80点、79点をとったとして test 関数を適用すると、

*Main> test 80
Just "Goukaku!"
*Main> test 79
Nothing

79点の人は問答無用の Nothing で門前払い。自分が何点合格まで足りなかったのかわからない。

 

Either a b 型の例

これでは受験生も納得できないだろうと考え、

「合格得点まで何点足りなかったのか?」

を返すように test 関数を変更することにした。

今度は Either a b 型を使い、合格を Right、不合格を Left で表現するとして test’ 関数を定義。

test' score = if score >= goukaku
              then Right "Goukaku!"
              else Left $ "Ato " ++ show (goukaku - score) ++ " ten tari nai"

先ほどと同じように、80点、79点をとったとして test’ 関数を適用すると

*Main> test' 80
Right "Goukaku!"
*Main> test' 79
Left "Ato 1 ten tari nai"

 

上記のように Maybe は Just で値を包まない限り Nothing が返され、それ以上何も伝えることができない。それに対して、Either では Maybe の Nothing に相当する Left でも何かを伝えることができる。

 

maybe と either 関数 の類似性

とは言ったものの、最初は Maybe a 型と Either a b 型がなぜ Prelude の Basic data types にあるのか全く見当がつかなかった。 (+_+)

Maybe によると、

Using Maybe is a good way to deal with errors or exceptional cases without resorting to drastic measures such as error.

これは 前回見た elemIndex 関数 のように、Maybe a 型は見つからなかったときに error で実行を止めてしまうのではなく、「なかった!」ということをこの関数の呼出し元に伝えるための方法であり、そのための型であるということ。

続いて Maybe の説明には次のように書かれている。

It is a simple kind of error monad, where all errors are represented by Nothing. A richer error monad can be built using the Data.Either.Either type.

(同上より)

この辺りで「ん?」 (@_@) … と。

Error モナドについては横に置いておくとして、エラーを伝える方法として Either は Maybe の親戚のようなものだと認識。

 

Data.Maybe, Data.Either から import されている関数      

ところで、Maybe, Either は、それぞれ Data.Maybe, Data.Either で定義されており、いくつか関数が定義されている。しかし、Prelude には各々一つの関数しか import されていない。それが以下の二つ。

maybe :: b -> (a -> b) -> Maybe a -> b

either :: (a -> c) -> (b -> c) -> Either a b -> c

最初、引数がごちゃごちゃしていてやだなぁ (@_@;) と感じた。しかし、説明を読めば、両者とも

第3引数 の値に応じて第1引数 もしくは 第2引数 が評価される関数

であることがわかる。

図示すれば、以下のように maybe と either の引数の間に対応関係がある。

091028-008

そして、第3引数の値が与えられると、返ってきた値に応じて第1引数、第2引数の式が評価される。

091102-003

either 関数に関しては、返ってきた値によって、文字通り Left または Rihgt にある関数が評価されるのでわかりやすい。

ちなみに、If-then-else – HaskellWiki には  if 式を関数に置き換えている例があるが、上記はこれに似ている。ただし、こちらは第1引数の値に応じて、第2第3引数が評価される。

if' :: Bool -> a -> a -> a
if' True  x _ = x
if' False _ y = y

… ということは、maybe, either 関数は、条件分岐の Maybe a, Either a b 型版と言ったところか。

追記 (2009.11.15)Data.Bool.HT パッケージに if’ が定義されている。(via Case – HaskellWiki )

 

試してみる

例えば、先ほどの test 関数の結果を第3引数に渡し、

「試験に合格した場合」と「不合格な場合」にかける言葉を返す hyouka 関数

を定義してみる。

hyouka = maybe "Zannen (;_;" (++ " omedetou! (^^") . test

例えば、

*Main> hyouka 80
"Goukaku! omedetou! (^^"
*Main> hyouka 79
"Zannen (;_;"

 091108-001

either 関数も同様に、

hyouka' = either (++ "nante zannen (+_+") (++ " omedetou! (^^") . test'

例えば、

"Goukaku! omedetou! (^^"
*Main> hyouka' 79
"Ato 1 ten tari nainante zannen (+_+"

 091108-002

2009年11月2日月曜日

おしゃれなトレンカの見分け方 - 2009年秋冬

1. タイツの違い

女性が履いている「黒いタイツ」のようなものには、微妙な違いがある。

なるほど... φ(Θ∇Θ)メモメモ

 

2. おしゃれなトレンカと、おばちゃんトレンカの違い

タイツに関する知識を、軽くひけらかしてみた。

(Θ∇Θ)y―~~

「駅のプラットホームにいた若い女の子が履いてたのは、レギンスでなくてトレンカだな。

まぁ、上の図で言えば、一番右のやつ。」

(知ったかぶり)

ボカン✿ー‿ー)ノ★(☉Д⊙)うげぇ~~~

 

違いのポイント

✿◕‿-)ノ” - Point -

「上図のトレンカは、通称おばちゃんトレンカ。昔からあるタイプで、正面から見るとかまぼこ形にくびれてます。

足の甲が半分くらい隠れるものを履かなければ、足長効果が得られません!

素材は、タイツタイプだと足首のラインがでるため、足の太さがわかってしまいます。できればタイツタイプでないものを選びましょう。」

ファッションって難しい。。 パタッ(o_ _)o~†

2009年11月1日日曜日

Haskell の フィールドラベル と デフォルト値をラップする関数

まいど、「名前」と「年齢」を持つ「人」型を例にとってフィールドラベルの使い方を覚える。
フィールドラベルを使わない場合の定義は、

data Person = Person String Int

1. 型を定義するとき

フィールドラベルを使うと、フィールドの意味が明確になる。
data Person = Person { name :: String
                     , age  :: Int
                     } deriving Show

2. 値を生成するとき

値を生成するときにフィールド名を指定できる
jirou = Person { name = "Jirou", age = 20 }

3. 値を取り出すとき

例えば、以下のような「人」の名前を取得するための関数を定義する必要がなくなる。
getName (Person n _) = n
代りに、フィールドラベルでフィールドの値を取得できる。
フィールド名は選択子関数として使用する。変数として使用するときは、 フィールド名はオブジェクトからそのフィールドを取り出す関数として働く。
(3.15.1 フィールドの選択 より、 太字は引用者による)
例えば、
tarou = Person "Tarou" 10
tarouName = name tarou
ただし、次のことに注意。
フィールドラベルは一般の変数やクラスメソッドとトップレベルの名前空間を共有します
(6.2 フィールドラベル より)
同じフィールド名がバッティングした場合、型ごとにモジュールに分けるなど対処が必要。(cf. Haskell のモジュールと型クラス)

4. パターンマッチのとき

例えば、年齢を 2 倍する関数をフィールドラベルを用いず書くとすると、
doubleAge (Person _ a) = a * 2
フィールドラベルを使うことによって、次のように書ける。
doubleAge (Person{ age = a }) = a * 2
つまり、必要なフィールドのみ書けばよい。なぜかこの書き方よく忘れる。。 (+_+)
ただし、この場合は上記の選択子関数を使った方がシンプルに書ける。
doubleAge = (* 2) . age

5. フィールドの更新

次のような年齢を変更する関数を定義する必要がなくなる。
setAge age (Person n _) = Person n age
あたかもフィールドを更新するかのように、
tarou' = tarou { age = 30 }

フィールドの省略について

ところで、フィールドラベルを使って値を生成するとき、特定のフィールドを省略できる。
hanako = Person { name = "Hanako" }
この場合、コンパイルすると警告がでるのみで、エラーとならない。
    Warning: Fields of `Person' not initialised: age
    In the expression: Person {name = "Hanako"}
    In the definition of `hanako': hanako = Person {name = "Hanako"}
Ok, modules loaded: Main.
ただし、「人」型の値から「年齢」を得ようとすると、次のような例外が発生する。
*Main> age hanako
*** Exception … : Missing field in record construction Main.age
つまり、実行時になってやっと判明する。 (+_+)

undefined を使った場合
これに対して、値を生成するとき undefined を使うと、コンパイル時に警告すら出ない。
hanako = Person "Hanako" undefined
しかし、当然ながら「年齢」を得ようとすると、実行時に例外が発生する。
*Main> age hanako'
*** Exception: Prelude.undefined
つまり、変数 hanako’ に上記の doubleAge 関数を適用すると、実行時にエラーとなる。
*Main> doubleAge hanako'
*** Exception: Prelude.undefined

データコンストラクタでデフォルト値を使いたい
例えば、
「名前」は確実にわかるけれど、「年齢」についてはわからない可能性がある
とする。上記のように undefined を使うと実行時エラーになる可能性があるので Haskell の型チェックの機能を十分に生かせない。
[Haskell-beginners] Default values for Data Types? には Maybe a 型と、データコンストラクタへのラッパー関数を作成して対応する方法が書かれていた。これを真似てみる。
まず「人」型の定義から。年齢を Maybe Int 型とする。
type Age = Maybe Int
data Person = Person { name :: String
                     , age  :: Age
                     } deriving Show
上記のデータコンストラクタは次のように使う。
tarou = Person "Tarou" (Just 10)
jirou = Person  "Jirou" Nothing
しかし、このように書くのは面倒なので、データコンストラクタをラップする関数 person を定義。
person = Person { name = "", age = Nothing }
これを使い、値を更新するふりをして、値を定義する。
hanako = person { name = "Hanako" }
フィールドラベルを書くのすら面倒なら、次のようなラッパー関数を定義。
person' n = Person n Nothing
先ほどよりもシンプルに書けるようになった。
akemi = person' "Akemi"

Maybe a 型を使うメリット
上記のように Maybe  a 型を使うといい理由は、Haskell がコンパイル時にエラーで教えてくれるから。
例えば、先ほどと同じように「年齢」を 2 倍にする関数を定義する。年齢がただの Int 型だと思い込んで次のように定義すると、
doubleAge' = (* 2) . age
コンパイル時にエラーが表示される。
    No instance for (Num Age)
      arising from the literal `2'
                   at C:\ …
    Possible fix: add an instance declaration for (Num Age)
    In the second argument of `(*)', namely `2'
    In the first argument of `(.)', namely `(* 2)'
    In the expression: (* 2) . age
Failed, modules loaded: none.
エラーの内容を読むと、Age 型、つまり、Maybe Int 型に (*) を適用するには、Maybe Int 型が Num クラスのインスタンスでないと無理だということ。実行時に突然エラーが表示されるのと違い、コンパイル時に関数適用の間違いを指摘してくれるので、実行する前にコードを修正できる。
例えば、年齢が未定義の場合、 2 倍しても 0 であるとするなら、次のように定義。
doubleAge (Person n a) = case a of
                           Nothing -> 0
                           Just x  -> x * 2

遅延評価させない
ところで、undefined とは、
A special case of error.
error とは、
error stops execution and displays an error message.
では、なぜ値を生成するとき undefined を指定できたのだろう?
6.3 正格データ構築子 によると、
Haskell ではデータ構造は一般的に遅延性をもちます。構成要素は必要になるまで評価されません。この性質のおかげで、データ構造はもし評価されるとエラーあるいは停止できないような要素を含むことができます。
ということは、遅延させなければ、エラーになるのだろうか?
data 宣言の中で、! でマークされたフィールドは、サンクに入れて遅延するのではなく、構造が生成される際に、直ちに評価されます。
(同上より)
上記の「サンク」とは、遅延評価 の説明において、、
遅延評価とは、… 評価しなければならない値が存在するとき、実際の計算を値が必要になるまで行わないことをいう。評価法が指示されているが実際の計算が行われていない中間状態の時それをプロミス (promise) や、計算の実体をさしてサンク (thunk) といい、プロミスを強制(force)することで値が計算される。
(太字は引用者による)
試してみる。下記のようにデータコンストラクトのフィールドの型の前に `!’ をつける。
data Person' = Person' { name' :: !String
                       , age'  :: !Int
                       }
先ほどと同じように一部のフィールドのみ定義すると、
hanako'' = Person' { name' = "Hanako" }
次のようにエラーが表示された。
    Constructor `Person'' does not have the required strict field(s): age'
    In the expression: Person' {name' = "Hanako"}
    In the definition of `hanako''':
        hanako'' = Person' {name' = "Hanako"}
Failed, modules loaded: none.