0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

fluorite-7 日本語チュートリアル Part 7 標準入力と文字列操作

Last updated at Posted at 2020-06-21

チュートリアルトップ

←前回 次回→

このパートでは、標準入力と簡単な文字列の加工について取り扱います。

レッスン1 標準入力

コンソール版fluorite-7では、組み込み定数INに標準入力を1行ずつ読み出すストリーマが格納されています。

$ echo -e 'abc\ndef' | fl7 'IN'
abc
def

INはストリーマであるため、パイプでそのまま1行ごとにデータを処理できます。

$ echo -e 'abc\ndef' | fl7 'IN | [_, _]'
abc,abc
def,def

レッスン2 文字列長

長さ演算子$#で文字列の長さが得られます。

$ fl7 '$#"abcdefg", $#"あ"'
7
1

全角文字も1文字としてカウントされますが、サロゲートペアは2文字としてカウントされます。


標準入力の1行ごとに処理ができるようになって、文字列長の取得という計算が可能になったので、何か処理を行ってみましょう。

cat /etc/nanorc | grep -vE '^#|^$'というbashコマンドでは以下のような出力が得られました(環境によります)。

$ cat /etc/nanorc | grep -vE '^#|^$'
set historylog
set locking
set nowrap
set suspend
include "/usr/share/nano/*.nanorc"

これにfl7 'IN | $#_'をくっつけてみましょう。

$ cat /etc/nanorc | grep -vE '^#|^$' | fl7 'IN | $#_'
14
11
10
11
34

set nowrap10に変換されました。
改行を含んでいない文字が_にやってきているのが分かります。

レッスン3 位置アクセス

「文字列[位置]」で、特定の位置にある文字を取り出します。
これをfluorite-7では位置アクセスと呼びます。

$ fl7 '"abcdefg"[4]'
e

負の位置を指定した場合、文字列の末尾から数えた位置の文字を取得します。
-1であれば最後の文字が得られます。

$ fl7 '"abcdefg"[-1]'
g

$ fl7 '"abcdefg"[-7]'
a

レッスン4 部分アクセス

「文字列[開始位置;終了位置]」で文字列の特定の一部分を切り出すことができます。
これをfluorite-7では部分アクセスと呼びます。
切り出される文字は、終了位置にある文字を含みません。
得られる文字列の長さは(終了位置-開始位置)になります。

$ fl7 '"abcdefg"[2; 5]'
cde

終了位置は省略できます。
終了位置を省略すると、文字列の末尾までを切り出します。

$ fl7 '"abcdefg"[2; ]'
cdefg

開始位置を省略すると、文字列の先頭からになります。

$ fl7 '"abcdefg"[; 5]'
abcde

両方省略したらどうなるでしょうか。

$ fl7 '"abcdefg"[; ]'
abcdefg

両方省略すると、文字列の先頭から末尾までを切り出します。
fluorite-7の文字列は不変オブジェクトなので、これをやる意味は特にないです。


こちらも負の位置指定ができます。

$ fl7 '"abcdefg"[-4; -1]'
def

これは末尾から4文字から、末尾から1文字目の手前までを抜き出します。

Tips 配列の切り出し

実は全く同じ指定の仕方が配列でもできます。

$ fl7 '[zero, one, two, three][2]'
two

$ fl7 '[zero, one, two, three][-1]'
three

$ fl7 '[zero, one, two, three][1; 3]'
one,two

$ fl7 '[zero, one, two, three][1; ]'
one,two,three

$ fl7 '[zero, one, two, three][; 3]'
zero,one,two

$ fl7 '[zero, one, two, three][; ]'
zero,one,two,three

$ fl7 '[zero, one, two, three][-3; -1]'
one,two

レッスン5 文字列のストリーマ展開

文字列に対して後置[]を置くと、文字のストリーマを得ます。

$ fl7 '"abcde"[]'
a
b
c
d
e

1文字ごとに処理を行うことができます。

$ fl7 '"abcde"[] | "[$(_)]"'
[a]
[b]
[c]
[d]
[e]

レッスン6 文字列結合

中置&は、左右の値を文字列として認識し、結合します。

$ fl7 '"Score: " & 400'
Score: 400

これは埋め込みと似ています。

$ fl7 '"Score: $(400)"'
Score: 400

レッスン7 文字列の繰り返し

中置*を文字列に対して行うと、その文字列を繰り返します。

$ fl7 '"abc" * 3'
abcabcabc

レッスン8 文字列化・数値化

前置&は値の文字列化、前置+は値の数値化を行います。

$ fl7 '&400, +"400"'
400
400

これだけでは分からないので、値の型を見てみましょう。

$ fl7 'TYPE(400), TYPE("400")'
NUMBER
STRING

$ fl7 'TYPE(&400), TYPE(+"400")'
STRING
NUMBER

&400STRING+"400"NUMBERとなりました。
データの変換が行われていることが分かります。


文字列の数値化は、文字列として格納されている数値を使用して算術を行う際に必須です。
例えば次のコードはどうなるでしょうか。

$ fl7 '"999" + 1'

このような「文字列として格納された数値」と数値の足し算の挙動は、プログラミング言語によってまちまちです。
fluorite-7では、中置+演算子は、左辺が文字列であれば文字列結合を行います。

$ fl7 '"999" + 1'
9991

この場合、999と1を足した1000を得るには、左辺を明示的に数値化します。

$ fl7 '+"999" + 1'
1000

他にも、数値同士を並べた数値を作るときに文字列の数値化が使えます。

$ fl7 '+(5 & 4 & 3) + 10000'
10543

5 & 4 & 3はこのままでは文字列なので+ 10000をすると54310000という文字列になってしまいますが、5 & 4 & 3+を付けることで543という数値を得て、それに10000を加算したので10543という数値が得られました。

レッスン9 JOIN関数・SPLIT関数

組み込み定数JOINには、ストリーマの各要素を文字列化し、,で結合する関数が入っています。

$ fl7 'JOIN(1 .. 4)'
1,2,3,4

これだけでは配列の文字列化と変わりありません。

$ fl7 '&[1 .. 4]'
1,2,3,4

しかし、JOIN関数は第2引数に結合に使う文字列を受け取れます。

$ fl7 'JOIN(1 .. 4; " / ")'
1 / 2 / 3 / 4

SPLIT関数はJOIN関数とは逆に、1個の文字列を,で分割し、ストリーマにします。

$ fl7 'SPLIT("1,2,3,4")'
1
2
3
4

SPLIT関数も同様に第2引数で分割文字列を受け取れます。

$ fl7 'SPLIT("1 / 2 / 3 / 4"; " / ")'
1
2
3
4

レッスン10 標準入力からのカラムの選択

前の方で出たこのコマンド出力の、historylog"/usr/share/nano/*.nanorc"の部分を取り出してみましょう。

$ cat /etc/nanorc | grep -vE '^#|^$'
set historylog
set locking
set nowrap
set suspend
include "/usr/share/nano/*.nanorc"

つまり、このような文字列の出力を目指します。

historylog
locking
nowrap
suspend
"/usr/share/nano/*.nanorc"

まずINだけを置くと、入力したものを何もせずそのまま出力します。
各行に対して処理を行いたいのでINにパイプを付けて行ごとに加工できるようにします。

$ cat /etc/nanorc | grep -vE '^#|^$' | fl7 'IN | _'
set historylog
set locking
set nowrap
set suspend
include "/usr/share/nano/*.nanorc"

_は恒等変換なので、このままでは入力したものをそのまま出力するだけです。

各行に対して空白で分割したいので、各行に対してSPLIT(_; " ")を適用します。
SPLIT関数はストリーマを返すので、[ ]で囲んで一旦配列にします。

$ cat /etc/nanorc | grep -vE '^#|^$' | fl7 'IN | [SPLIT(_; " ")]'
set,historylog
set,locking
set,nowrap
set,suspend
include,"/usr/share/nano/*.nanorc"

区切りが,になりました。あとは添え字1の要素を取得すれば完成です。

$ cat /etc/nanorc | grep -vE '^#|^$' | fl7 'IN | [SPLIT(_; " ")][1]'
historylog
locking
nowrap
suspend
"/usr/share/nano/*.nanorc"

まとめ

  • INで標準入力を1行ずつ読み込む。
  • $#stringで文字列長が得られる。
  • string[index]で文字が得られる。
  • 負の位置を指定すると末尾から数える。
  • string[start; end]で部分文字列が得られる。
  • 部分文字列の開始・終了位置は省略できる。
  • string[]で文字のストリーマを得る。
  • value1 & value2は文字列として結合する。
  • string * numberで文字列を繰り返す。
  • &valueで文字列化、+valueで数値化する。
  • JOINでストリーマを特定の文字列で結合できる。
  • SPLITで文字列を特定の文字列で分割してストリーマにできる。

Part 8

次回→

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?