今日は前にやった内容の 復習をしますが
じっくりやってください。
文字、文字列、シンボルです。
今日学ぶことは 文字の扱い方や
文字列の表現や
文字列とシンボルの関係についてです。
では始めましょう。 文字です。
Pharo では文字は ドルマークで始まり
それに文字が続きます。
こうやって文字のリテラルを表現します。
非表示文字は
空白やタブや
改行などがありますが
Character クラスに メッセージを送ることで
こういった文字を得ることができます。
では文字列です。
文字列は引用符（'）で囲まれています。
この文字です。
ここに文字列「eclair au chocolat」 があります。
ここから始まって、ここで終わります。
文字列にメッセージを送ることができます。 例えば、size です。
すると 18 が返ってきます。
実際、この文字列は 18 文字から成っています。
もっと色々と文字列を操ることができます。
例えば、 Character space split: とすると
引数の文字列が空白で切り分けられて
3 つの要素からなる OrderedCollection （順序つきコレクション）が得られます。
文字列が 3 つに切り分けられるわけです。
Pharo では、文字列はコレクションです。
本当に文字の列になっています。
String クラスは Collection クラスから 継承しているので
Collectionのメソッドを 使うことができます。
よく使われるコレクションクラスがあります。
例えば IndexedCollection では at: があります。
'eclair au chocolat' at: 1
とすると、このコレクションの 1 番目の要素として「e」が得られます。
この「e」です。
do: を使って要素を 走査することもできます。
ループの中でブロックが
コレクションの 1 文字目、2 文字目 とセットしていきます。
1 つ、細かなことですが
文字列は引用符（'）で区切られるのですが
文字列中に引用符を入れたい時には
引用符（'）を 2 つ連続して入れてください。
こうすることで、文字列中に 1 つの引用符（'）を入れることができます。
ただし、文字列の中で
その引用符は 1 文字として扱われます。
例えば 'L''eclair au chocolat' at: 2
とすると、このコレクションの 2 番目の要素として
引用符「'」が返ってきます。
そして at: 3 とすると ここにある「e」が得られます。
引用符を 2 つ書き込んでも それは 1 文字として扱われます。
文字列は他のコレクションと同じように 扱うことができます。
文字列の最後の要素を得るためには
str at: str size とすることができます。
忘れてはいけないのは、Pharo では インデックスが 1 から始まることです。
したがって、文字列のサイズが 最後の文字のインデックスになります。
あるいは、単に last を送ることで 最後の要素を得ることができます。
文字列を生成するためには いろいろなやり方があります。
簡単なのは変換メソッドを使うことです。
シンボルを文字列に変換するには asString メッセージを使います。
あるいは、どんなオブジェクトに対しても printString を送ることができます。
すると、そのオブジェクトの 文字列表現が得られます。
あるいは、コレクション生成メソッドを 直接使ううことで文字列を生成できます。
任意のコレクションクラスに with: を送ることで
引数として渡した要素を含むコレクションを 生成することができます。覚えていますよね。
String with: $A とすると
1 文字「A」からなる文字列が得られます。
文字列を連結するためには
もう見たと思いますが、コンマを使います。
「,」を文字列に送って 引数として文字列を渡すと
それら 2 つの文字列を連結した 新しい文字列を生成します。
ただし、気をつけなければならないのは
この例のようなことをすると
無用な中間生成物をつくってしまう ということを忘れないでください。
つまり、この文字列に 最初の , メッセージを
この引数で送ると
最初の連結文字列が生成されます。
この連結文字列に , を送ると
また別の連結文字列が生成されて それが最終的な返り値になります。
中間文字列が生成されてしまい
計算時間の無駄になります。
ベンチマークの講義がありましたね。
何が起こっているのか ベンチマークで見て
そしてストリームを使うべきか 判断してください。
文字列を生成するために
streamContents: を使って
このストリームに文字を直接送り込んで 最終的な文字列を生成することができます。
この方法を使うと、文字列が中間生成される のを避けることができます。
さて、シンボルですが
構文的には シンボルはハッシュタグで始まります。
そして文字列が続きます。
これがシンボルのリテラルです。
これはある種の文字列ですが システム内でユニークな文字列です。
プログラムのどこかで ハッシュタグに続いて「ほげほげ」書くと
プログラム中の他の箇所での ハッシュタグ「ほげほげ」は
同一のオブジェクトを指すことになります。
同じインスタンスを指すということです。
これがシンボルはユニークということです。
ここに #calvin == #calvin とありますが true になります。
同一オブジェクトということです。
文字列の場合はそうはなりません。 場合によります。
コンパイラの最適化によって 変わってきます。
これがシンボルと文字列の違いです。
シンボルは完全にリードオンリーです。
シンボルは書き換えることができません。 新しいシンボルを生成する必要があります。
シンボルはユニークなオブジェクト つまり常に同じオブジェクトを指します。
文字列はミュータブルなオブジェクトで 内容を書き換えることができます。
今のところは。実際のところ 現在まだ議論の対象になっています。
シンボルはメソッドセレクターとして
よく使われます。
そしてシンボルは辞書（Dictionary）の
キーとして有用です。
IdentityDictionary を
知っていますか？
辞書のキーとして使うと
比較のためにハッシュを計算して
辞書の中に格納します。
この講義で重要なことは
文字列は他のコレクションと同様であること
そしてシンボルはユニークであり
リードオンリーで イミュータブルであることです。