LoginSignup
0
0

More than 5 years have passed since last update.

perl6 のワンライナー

Last updated at Posted at 2016-01-06

20160105

正月休みに、触ってみたものの、、、

取り敢えずメモったの。

バージョン
$ perl6 -v 
This is Rakudo version 2015.12 built on MoarVM version 2015.12
implementing Perl 6.c.

コマンドラインスイッチ

ここ

  • -i が消えたのはちょっと残念
  • -l はデフォルトの挙動になったので削除されている。

-a

実装予定はある様だが、今の所は実装されてない(?)。

.split を使えとの事だが、 .words っつーのもある。

-0

外した理由は、ここ

これ外して欲しくないなあ。ごく稀にしか使わんかったけど。

特殊変数

@*ARGS

@ARGV

$ perl6 -e '.say for @*ARGS' 1 2 3 4 5 
1
2
3
4
5
$ perl6 -e '@*ARGS.say' 1 2 3 4 5
[ 1 2 3 4 5 ]
$ perl6 -e '@*ARGS[2].say' 1 2 3 4 5
3

配列の要素へのアクセスが、 $arr[0] じゃない事に留意。

$*ARGFILES

ワンライナーでのファイルハンドルは、 $*ARGFILES

$ perl6 -ne '.say if $*ARGFILES.eof' SOMETHING.txt
  • $*ARGFILES.filename で、perl5$ARGV
  • $*ARGFILES.ins で、perl5$.
  • $*ARGFILES.eof で、perl5eof()
    • eof の挙動ではなく eof() なので注意

.eofeof() の挙動しかないのだったら、ワンライナー使いにはちょっと厳しい、、、

$

$. が廃止。

その代りに、登場した anonymous な変数

$ perl6 -ne 'say ++$ ~ ": $_"' SOMETHING.txt
  • ~ で連結

一見、$*ARGFILES.ins よりも短かくなって、良さげだが、lexical scope 毎に別制御

$ perl6 -ne '++$; say $' SOMETHING.txt
(Any)
(Any)
(Any)
$ perl6 -ne 'state $a; $a =  ++$ ; say $a' SOMETHING.txt
1
2
3

$a = ++$ な事するくらいだったら、普通に ++$a する。

使い方によっては強力だろう。

演算子

Flipflop operator.

perl5 の range operator のスカラーコンテキストでの挙動が、切り離された。
ここff がらみの所。

定番の FASTA 切り出し。
perl5 では、こんな感じ

perl6
$ perl6 -ne '.say if /\>gi\|blah/ fff^ /\>/' MULTIFASTA

以前の .f に代り、...fff に。
で、^ で含まず指定。

  • E0 判定せずに済むので、その分かなり楽っちゃー楽。
  • > がメタ文字になっちゃったのでエスケープが必要。
  • $. が廃止。つーことで、暗黙の行番号範囲指定も出来なくなった。

range operator

range operator は更に二つの別物から構成されてるっぽい。

  • infix ..
  • infix ...

適当にコードを実行したものをメモ

$ perl6 -e 'say 1..4'
1..4
$ perl6 -e 'say 1...4'
(1 2 3 4)

この時点で、返すものが違う

$ perl6 -e 'say 2 ~~ 1..4' 
True
$ perl6 -e 'say 2 ~~ 1...4'
(False True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True True ...)

スマートマッチでも挙動が違う。

$ perl6 -e 'say 4..1'
4..1
$ perl6 -e 'my @a = 4..1 ; say @a'
[]
$ perl6 -e 'say 4...1'
(4 3 2 1)

逆順range は、 ... の方だけ。

$ perl6 -e 'my @a = 1 ^..^ 4 ; say @a'
[2 3]
$ perl6 -e 'my @a = 1 ...^ 4 ; say @a
[1 2 3]

含まず指定は、 ... では末尾のみ。

$ perl6 -e 'say 1 .. 4 Z~ 1 .. 4'
(11 22 33 44)
$ perl6 -e 'say  ( 1 ... 4 ) Z~ (1 ... 4 )'
(11 22 33 44)

zip するのに括弧なりが必要。

おおっ

$ perl6 -e '.say for q{01} .. 12 '
01
02
03
04
05
06
07
08
09
10
11
12

おお、、、orz...

$ perl6 -e '.say for 12 ... q{01} ' | head -10
12
13
14
15
16
17
18
19
20
21

三項演算子

条件 ?? 真の時の値 !! 偽の時の値
$ perl6 -ne 'say  /a/ ?? $_ !! q{no}' SOMETHING.txt

Reduction operators

$ perl6 -e '( [+] @*ARGS).say' 1 2 3 4 5
15
$ perl6 -e '( [~] @*ARGS).say' 1 2 3 4 5
12345

[] の中に演算子

BEGIN, END

$ perl6 -ne 'BEGIN { 42.say ; };  END { 42.say ; };  .say ' SOMETHING.txt

BEGIN, END ブロックはそれぞれ健在

  • 但し、ブロックの後にセミコロン必須
  • キーワード(BEGIN とか)の後にスペース必須

sort

$ perl6 -e '@*ARGS.sort({ $^a <=> $^b }).say' 10 9 3 1 2
(1 2 3 9 10)
$ perl6 -e '@*ARGS.sort({ $^a.chars, $^a}).say' 10 9 3 1 2 
(1 2 3 9 10)
  • デフォでは文字列ソート
  • $a, $b の代りは、 $^a, $^b つか、 $^ がキモで後は、[a-z]
  • $^a.chars はタイプ数が増えるだけだから、覚える必要無いか?

reverse/complement

$ perl6 -e 'q{ACACTTTGC}.trans("ACGT" => "TGCA").flip.say' 
GCAAAGTGT
  • tr///.trans に。
  • scalarreverse は、 .flip に。
$ perl6 -e 'q{ACACTTTGC}.trans("ACGT" => "TGCA").reverse.say' 
(TGTGAAACG)

listreverse は、また別で、意図せずコードが動きやがるところが、どーにも。

50base 区切り

実行速度とか検討の余地あるが、 perl5 のバージョンをそのまま移したら。

$ perl6 -e 'my $a = q{A} x 98 ; $a ~~ s:g/(.**1..50)/$0\n/ ; $a.print' 
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
  • (.{1,50}) は、(.**1..50) に。
  • $1 は、 $0 に。
  • /g 修飾子は、 :g/ の形に。

先読み言明

$ perl6 -e 'my $a = qq{>A\n} ~ q{a} x 20 ~ qq{\n} ; $a ~= $a  ; $a ~~ s:g/<before \>A >/\n/ ; $a.say '

>A
aaaaaaaaaaaaaaaaaaaa

>A
aaaaaaaaaaaaaaaaaaaa

  • (?=>) が、 <before \> > に。
    • 文字クラス(?)利用の <?[>]> の方が、見た目はすっきりする。

言明については、ここ

ハイパー演算子

バージョンによって挙動が違うかも

@a <<OP<< @b

OP には、演算子。

積算とかさせるのに便利かなーっと思ったので。

$ cat test.txt
1   2   3
4   5   6
7   8   9
$ perl6 -e 'my @a = (0,0,0) ;  @a <<+=<< .words for @*ARGS[0].IO.lines ; say @a ' test.txt
[12 15 18]

この例では、 @a の各要素に、 += で積算してる。

素直に、

$ perl6 -ne 'state @a =(0,0,0); @a <<+=<< .words; say @a if $*ARGFILES.eof' test.txt

こう書きたいのに、state がまともに機能してくれません。scope の仕様だろうけど、変更は無いのだろうか。

use vars に該当するモジュールは、無いわけだし、、、

Discouraged in Perl 5. See http://perldoc.perl.org/vars.html.
You should refactor your Perl 5 code to remove the need for use vars, before translating into Perl 6.
引用元

普通に動かせば state が機能する

$ perl6 -e 'for q{test.txt}.IO.lines { state @a = (0,0,0) ; @a <<+=<< .words ; say @a  }'
[1 2 3]
[5 7 9]
[12 15 18]

感覚的にちょっと

拡張する、って言うんだから、+= の時も拡張して欲しい。

$ perl6 -e 'my @a = ( 0 ) ; my @b = (1,2,3) ; @a <<+=<< @b ; @a.say'
[6]
$ perl6 -e 'my @a = ( 0 ) ; my @b = (1,2,3) ; @a = @a <<+<< @b ; @a.say'
[1 2 3]
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