From db3d51ddc421dad68abddb95d01ffdab440197d6 Mon Sep 17 00:00:00 2001 From: nsfisis Date: Sun, 19 Mar 2023 03:24:43 +0900 Subject: feat(content): specify heading id --- content/posts/2021-03-30/phperkaigi-2021.xml | 38 +- .../2021-10-02/ruby-then-keyword-and-case-in.xml | 12 +- .../rust-where-are-primitive-types-from.xml | 6 +- ...ce-between-autocmd-bufwrite-and-bufwritepre.xml | 223 +++-- .../vim-swap-order-of-selected-lines.xml | 38 +- .../posts/2022-04-09/phperkaigi-2022-tokens.xml | 40 +- ...anner-write-tool-showing-banner-in-terminal.xml | 6 +- content/posts/2022-05-01/phperkaigi-2022.xml | 12 +- .../php-conference-okinawa-code-golf.xml | 12 +- .../support-for-communty-is-employee-benefits.xml | 2 +- .../write-fizzbuzz-in-php-2-letters-per-line.xml | 955 ++++++++++----------- public/posts/2021-03-30/phperkaigi-2021/index.html | 76 +- .../ruby-then-keyword-and-case-in/index.html | 24 +- .../rust-where-are-primitive-types-from/index.html | 12 +- .../index.html | 112 +-- .../vim-swap-order-of-selected-lines/index.html | 46 +- .../2022-04-09/phperkaigi-2022-tokens/index.html | 80 +- .../index.html | 12 +- public/posts/2022-05-01/phperkaigi-2022/index.html | 24 +- .../php-conference-okinawa-code-golf/index.html | 24 +- .../index.html | 4 +- .../index.html | 64 +- 22 files changed, 910 insertions(+), 912 deletions(-) diff --git a/content/posts/2021-03-30/phperkaigi-2021.xml b/content/posts/2021-03-30/phperkaigi-2021.xml index 745db4b..ab682b9 100644 --- a/content/posts/2021-03-30/phperkaigi-2021.xml +++ b/content/posts/2021-03-30/phperkaigi-2021.xml @@ -17,7 +17,7 @@ -
+
PHPerKaigi 2021 参加レポ 2021-03-26 から 2021-03-28 @@ -34,7 +34,7 @@ 発表はトラック A、B に分かれていたのだが、今回はすべて A トラックを視聴している (切り替えるのが面倒だっただけ)。 -
+
凡例
@@ -45,9 +45,9 @@ 感想など
-
+
Day 0 前夜祭 (2021/03/27) -
+
17:30 [A] PHP で AWS Lambda @@ -103,7 +103,7 @@ だという先入観を持っていたのだが、この発表のデモによればそうでもないらしい。
-
+
18:10 [A] 大規模サイトの SEO @@ -155,7 +155,7 @@ は大して知らないので新鮮な話が多かった。その分語れることも少ない……。
-
+
18:50 [A]
@@ -217,7 +217,7 @@ いわゆる「健常者」にとって、こうした問題を普段の生活の中で意識するのは難しい。だからこそ情報へのアンテナは張っておくようにしたい。
-
+
19:30 [A] PHP で FUSE @@ -284,9 +284,9 @@
-
+
Day 1 (2021/03/27) -
+
10:50 [A] ATDD @@ -380,7 +380,7 @@ 高レベルテストの自動化は現在のプロジェクトでも感じており、自動化のチャンスは伺っている。とはいえセッションでも指摘されているように自動化することにコストがかかりすぎる領域があるのも事実で、そのバランスが難しい。
-
+
11:50 [A] 型解析を用いたリファクタリング @@ -421,13 +421,13 @@ Ruby の typeprof には注目している。
-
+
12:30 [A] 昼食をとっていた。事前に何か食料を買っておくべきだった。
-
+
13:10 [A] Documentation as Code @@ -490,7 +490,7 @@ 情報を起点にするのは理にかなっている。問題はトレースをいつ、どう取るかだろうか。それを自動化しなければ、実態との乖離が避けられないだろう。
-
+
14:10 [A] cookie による session 管理 @@ -500,7 +500,7 @@ やセッションの話としては非常に分かりやすくまとめられていたので、知らない人が学ぶにはいい教材だろう。
-
+
14:50 [A] PHP のエラーと例外 @@ -613,7 +613,7 @@ のように、すでに例外が言語システムに根ざしている言語ではどうすればよいか。この場合も同じく静的検証の力を借りることになるだろう。
-
+
15:30 [A] Laravel のメール認証 @@ -623,7 +623,7 @@ の知識がない私にはまったくついていけなかった。また、個人的にタイトルがややミスリーディングに感じた。
-
+
16:10 [A] gRPC @@ -677,7 +677,7 @@ というエコシステムに乗れることのメリットが大きいと感じる。そのエコシステムにうまく乗れない時点で、うーんという感じ。
-
+
16:50 [A] アーキテクチャテスト @@ -726,7 +726,7 @@
-
+
Day 2 (2021/03/28) 冒頭に書いた通り、2日目から体調が悪くまともに聴けていない。途中までは頭痛を我慢しつつ見ていたのだが、まともに入ってこなかった。 @@ -735,7 +735,7 @@ 残念ではあるが、いずれにせよ見られていない発表は他にもあるので、今週末にでもまとめて見ようと思う。
-
+
全体の感想 Day 2 diff --git a/content/posts/2021-10-02/ruby-then-keyword-and-case-in.xml b/content/posts/2021-10-02/ruby-then-keyword-and-case-in.xml index 40ac316..00afc01 100644 --- a/content/posts/2021-10-02/ruby-then-keyword-and-case-in.xml +++ b/content/posts/2021-10-02/ruby-then-keyword-and-case-in.xml @@ -23,14 +23,14 @@
-
+
TL; DR case - in によるパターンマッチング構文でも、case - when と同じように then が使える (場合によっては使う必要がある)。
-
+
<literal>then</literal> とは 使われることは稀だが、Ruby では then @@ -75,7 +75,7 @@ ]]>
-
+
なぜ普段は書かなくてもよいのか 普通 Ruby のコードで then @@ -116,7 +116,7 @@ 無事 Hello, World! と出力されるようになった。
-
+
なぜ <literal>then</literal> や <literal>;</literal> や改行が必要か なぜ then; や改行 (以下 「then 等」) @@ -158,7 +158,7 @@ が代用できるので、ほとんどの場合 then は必要ない。
-
+
<literal>case</literal> - <literal>in</literal> における <literal>then</literal> ようやく本題にたどり着いた。来る Ruby 3.0 では casein @@ -257,7 +257,7 @@ ]]>
-
+
まとめ diff --git a/content/posts/2021-10-02/rust-where-are-primitive-types-from.xml b/content/posts/2021-10-02/rust-where-are-primitive-types-from.xml index f395f4f..7c19fc5 100644 --- a/content/posts/2021-10-02/rust-where-are-primitive-types-from.xml +++ b/content/posts/2021-10-02/rust-where-are-primitive-types-from.xml @@ -22,7 +22,7 @@
-
+
前置き Rust @@ -63,7 +63,7 @@
-
+
調査 調査に使用したソース (調査時点での最新 master) @@ -230,7 +230,7 @@ という名前の別の型が見つかるからだ。
-
+
まとめ Rust diff --git a/content/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre.xml b/content/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre.xml index 2a61fb4..4e3f187 100644 --- a/content/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre.xml +++ b/content/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre.xml @@ -22,13 +22,13 @@
-
+
TL; DR 違いはない。ただのエイリアス。
-
+
調査記録 Vim の autocmd events には似通った名前のものがいくつかある。大抵は @@ -56,114 +56,113 @@
ソースコードへのリンク - vim - (調査時点での master branch) - neovim - (上に同じ) - -
-
- vim のソースコード - - 以下は、autocmd events - の名前と内部で使われている整数値とのマッピングを定義している箇所である。見ての通り、上でエイリアスではないかと述べた3組には、それぞれ同じ内部値が使われている。 - - - https://github.com/vim/vim/blob/8e6be34338f13a6a625f19bcef82019c9adc65f2/src/autocmd.c#L85-L86 - - - - - - https://github.com/vim/vim/blob/8e6be34338f13a6a625f19bcef82019c9adc65f2/src/autocmd.c#L95-L97 - - - - - - https://github.com/vim/vim/blob/8e6be34338f13a6a625f19bcef82019c9adc65f2/src/autocmd.c#L103-L105 - - - - -
-
- neovim のソースコード - - neovim の場合でも同様のマッピングが定義されているが、こちらの場合は Lua - で書かれている。以下にある通り、はっきり aliases と書かれている。 - - - https://github.com/neovim/neovim/blob/71d4f5851f068eeb432af34850dddda8cc1c71e3/src/nvim/auevents.lua#L119-L124 - - - - - - ところで、上では取り上げなかった FileEncoding だが、これは - :help FileEncoding にしっかりと書いてある。 - - *FileEncoding* - - -
-
- まとめ - - 記事タイトルについて言えば、どちらも変わらないので好きな方を使えばよい。あえて言えば、次のようになるだろう。 - - - - BufAdd/BufCreate - - BufCreate は歴史的な理由により ("for historic reasons") 存在しているため、新しい方 (BufAdd) を使う - - - - BufRead/BufReadPost - - BufReadPre との対称性のため、あるいは BufWritePost との対称性のため BufReadPost を使う - - - - BufWrite/BufWritePre - - BufWritePost との対称性のため、あるいは BufReadPre との対称性のため BufWritePre を使う - - - - FileEncoding/EncodingChanged - - FileEncoding`Obsolete'' と明言されているので、`EncodingChanged を使う - - - - - ところでこの調査で知ったのだが、BufReadBufWrite - は上にある通り発火するタイミングが「後」と「前」で対称性がない。可能なら - Pre/Post 付きのものを使った方が分かりやすいだろう。 - -
-
+ vim (調査時点での master branch) + neovim (上に同じ) + + +
+ vim のソースコード + + 以下は、autocmd events + の名前と内部で使われている整数値とのマッピングを定義している箇所である。見ての通り、上でエイリアスではないかと述べた3組には、それぞれ同じ内部値が使われている。 + + + https://github.com/vim/vim/blob/8e6be34338f13a6a625f19bcef82019c9adc65f2/src/autocmd.c#L85-L86 + + + + + + https://github.com/vim/vim/blob/8e6be34338f13a6a625f19bcef82019c9adc65f2/src/autocmd.c#L95-L97 + + + + + + https://github.com/vim/vim/blob/8e6be34338f13a6a625f19bcef82019c9adc65f2/src/autocmd.c#L103-L105 + + + + +
+
+ neovim のソースコード + + neovim の場合でも同様のマッピングが定義されているが、こちらの場合は Lua + で書かれている。以下にある通り、はっきり aliases と書かれている。 + + + https://github.com/neovim/neovim/blob/71d4f5851f068eeb432af34850dddda8cc1c71e3/src/nvim/auevents.lua#L119-L124 + + + + + + ところで、上では取り上げなかった FileEncoding だが、これは + :help FileEncoding にしっかりと書いてある。 + + + + +
+
+
+ まとめ + + 記事タイトルについて言えば、どちらも変わらないので好きな方を使えばよい。あえて言えば、次のようになるだろう。 + + + + BufAdd/BufCreate + + BufCreate は歴史的な理由により ("for historic reasons") 存在しているため、新しい方 (BufAdd) を使う + + + + BufRead/BufReadPost + + BufReadPre との対称性のため、あるいは BufWritePost との対称性のため BufReadPost を使う + + + + BufWrite/BufWritePre + + BufWritePost との対称性のため、あるいは BufReadPre との対称性のため BufWritePre を使う + + + + FileEncoding/EncodingChanged + + FileEncoding`Obsolete'' と明言されているので、`EncodingChanged を使う + + + + + ところでこの調査で知ったのだが、BufReadBufWrite + は上にある通り発火するタイミングが「後」と「前」で対称性がない。可能なら + Pre/Post 付きのものを使った方が分かりやすいだろう。 + +
diff --git a/content/posts/2021-10-02/vim-swap-order-of-selected-lines.xml b/content/posts/2021-10-02/vim-swap-order-of-selected-lines.xml index f50a8a0..f919301 100644 --- a/content/posts/2021-10-02/vim-swap-order-of-selected-lines.xml +++ b/content/posts/2021-10-02/vim-swap-order-of-selected-lines.xml @@ -22,7 +22,19 @@
-
+
+ TL; DR + + ,g/^/m-1 + ]]> + +
+
バージョン情報 :version の一部 @@ -34,9 +46,9 @@
-
+
よく紹介されている手法 -
+
<literal>tac</literal> / <literal>tail</literal> tactail -r などの外部コマンドを ! @@ -52,7 +64,7 @@ オプションは環境によって利用できないことがあり、複数の環境を行き来する場合に採用しづらい
-
+
<literal>:g/^/m0</literal> こちらは外部コマンドに頼らず、Vim の機能のみを使う。g:global @@ -99,7 +111,7 @@
-
+
<literal>:g/^/m0</literal> の問題点 :global @@ -114,7 +126,7 @@
-
+
解決策
@@ -177,7 +189,7 @@ の呼び出しをユーザー定義関数に切り出すことで上述の問題を解決できる。
-
+
解決策 (改訂版)
@@ -203,16 +215,4 @@
-
- コピペ用再掲 - - ,g/^/m-1 - ]]> - -
diff --git a/content/posts/2022-04-09/phperkaigi-2022-tokens.xml b/content/posts/2022-04-09/phperkaigi-2022-tokens.xml index e3d9c45..352eba0 100644 --- a/content/posts/2022-04-09/phperkaigi-2022-tokens.xml +++ b/content/posts/2022-04-09/phperkaigi-2022-tokens.xml @@ -33,7 +33,7 @@ リポジトリはこちら: https://github.com/nsfisis/PHPerKaigi2022-tokens
-
+
第1問 brainf_ck.php ソースコードはこちら。実行には PHP 8.1 以上が必要なので注意。 @@ -114,16 +114,16 @@ この問題は、単に適切なバージョンの PHP で動かせばトークンが得られる。 -
+
解説 -
+
絵文字 まず目につくのは大量の絵文字だろう。 PHP は識別子に使用できる文字の範囲が広く、絵文字も使うことができる。
-
+
プログラム全体 Brainf*ck のインタプリタとプログラムになっている。 Brainf*ck @@ -185,7 +185,7 @@ なお、$🐘 はいわゆる main 関数であり、プログラムの実行部分である。
-
+
絵文字の選択 おおよそ意味に合致するよう選んでいるが、$🤡$🎪 @@ -193,7 +193,7 @@ のマスコットの象に由来する。
-
+
strict_types declare 文の strict_types に指定できるのは、01 @@ -201,7 +201,7 @@ 8.1 から追加された、0O または 0o から始まる八進数リテラルを使った。
-
+
URL ソースコードのライセンスを示したこの部分だが、 @@ -216,7 +216,7 @@ 以降は行コメントになっている。
-
+
リテラルなしで数値を生成する ソースコード中に、ほとんど数値リテラルが書かれていないことにお気づきだろうか。 @@ -245,7 +245,7 @@ にし、さらにビット反転して -1 にしている。
-
+
<literal>if</literal> 文なしで条件分岐 三項演算子ないし match 式を使うことで、if @@ -254,7 +254,7 @@ のような形で分岐することもできる。
-
+
<literal>while</literal>、<literal>for</literal> 文なしでループ 不動点コンビネータを使って無名再帰する @@ -273,7 +273,7 @@
-
+
第2問 riddle.php ソースコードはこちら。実行には PHP 8.0 以上が必要なので注意。 @@ -324,7 +324,7 @@ ここでは、私の想定解を解説する。 -
+
読解 まずはソースコードを読んでいく。 @@ -372,7 +372,7 @@ 5文字ごとに区切ったあと、改行で結合している。
-
+
ヒント 次に、ソースコードに書いてあるヒントを読んでいく。 @@ -390,7 +390,7 @@ ファイルに追加ヒントとして書かれている)。
-
+
解く ここまでわかれば、あと一歩で解ける。すなわち、0x14B499C# @@ -455,7 +455,7 @@
-
+
第3問 toquine.php ソースコードはこちら。 @@ -504,9 +504,9 @@ 実際にはもう少しパイプで繋げなければならない。 -
+
解説 -
+
プログラム全体 コメントにもあるとおり、これは quine (風) のプログラムになっている。 @@ -518,14 +518,14 @@ 異なるのはトークンになっている部分のみである。
-
+
トークン $xs がトークンに対応している。変換のロジックは riddle.php とほぼ同じなので省略する。
-
+
状態保持 トークンの何文字目まで出力したかを、ソースコードを変えずに (quine @@ -534,7 +534,7 @@ から情報を取得している。
-
+
ROT 13 Quine は、素朴に書くとプログラムの一部が 2回記述されてしまう。 diff --git a/content/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal.xml b/content/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal.xml index f80a730..a98f94e 100644 --- a/content/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal.xml +++ b/content/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal.xml @@ -37,7 +37,7 @@ リポジトリはこちら: https://github.com/nsfisis/term-banner
-
+
Motivation 以前、https://github.com/nsfisis/big-clock-mode[big-clock-mode] @@ -64,7 +64,7 @@ まあ、作らなくても探せばあると思うが、作りたいものは作りたいので知ったことではない。
-
+
プログラム 全体の流れは次のようになっている。 @@ -85,7 +85,7 @@ 仕事ではスクリプト言語ばかり書いているが、やはりコンパイル言語はいい。
-
+
フォント フリーの 8x8 diff --git a/content/posts/2022-05-01/phperkaigi-2022.xml b/content/posts/2022-05-01/phperkaigi-2022.xml index 1290abd..621fcde 100644 --- a/content/posts/2022-05-01/phperkaigi-2022.xml +++ b/content/posts/2022-05-01/phperkaigi-2022.xml @@ -30,9 +30,9 @@ 昨年のレポートはこちら。
-
+
感想 -
+
厳選おすすめトーク 多くの素晴らしいトークの中から、特におすすめのものを @@ -111,14 +111,14 @@
-
+
トークン問題の作成 今回は、PHPer チャレンジ用に弊社のトークン問題を 3題作成した。こちらについては別途記事にしているので、そちらを参照されたい。
-
+
PHPer チャレンジ 1位になった。
@@ -126,7 +126,7 @@ をいただいた。
-
+
カンファレンス全体への感想 去年の参加レポ @@ -157,7 +157,7 @@
-
+
そして来年へ……? PHPerKaigi 2023 があるかどうか存じ上げないが、あるとすれば、次の diff --git a/content/posts/2022-08-27/php-conference-okinawa-code-golf.xml b/content/posts/2022-08-27/php-conference-okinawa-code-golf.xml index 76fc041..581dcb4 100644 --- a/content/posts/2022-08-27/php-conference-okinawa-code-golf.xml +++ b/content/posts/2022-08-27/php-conference-okinawa-code-golf.xml @@ -33,7 +33,7 @@ https://speakerdeck.com/memory1994/php-conference-okinawa-2022-extra?slide=3
-
+
細かいレギュレーションは不明だったので、勝手に定めた。 @@ -74,9 +74,9 @@ ]]>
-
+
使用したテクニック -
+
指数表記 割と多くの言語のゴルフで使えるテクニック。e @@ -84,7 +84,7 @@ 10000500020001000 を指数表記している。
-
+
foreach や for の中身を1つの文に foreachforif などの後ろには、通常 { @@ -92,7 +92,7 @@ を省略できる。C言語などでも使える。
-
+
$r に初期値を入れない PHP では、$r[] = …​ @@ -111,7 +111,7 @@ バイト縮む。
-
+
PHP タグの外に文字列を置く PHP では、<?php ?> diff --git a/content/posts/2022-08-31/support-for-communty-is-employee-benefits.xml b/content/posts/2022-08-31/support-for-communty-is-employee-benefits.xml index a28b96d..02fbe93 100644 --- a/content/posts/2022-08-31/support-for-communty-is-employee-benefits.xml +++ b/content/posts/2022-08-31/support-for-communty-is-employee-benefits.xml @@ -30,7 +30,7 @@ 本件を社内でしつこく推進した1人として、推進の理由等を書き残しておきます。
-
+
なぜ? 組織としての寄付理由は前掲した記事に譲るとして、ここでは、私が社内でこの件を推進した理由について書くことにします。 diff --git a/content/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line.xml b/content/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line.xml index d39526a..d828554 100644 --- a/content/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line.xml +++ b/content/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line.xml @@ -19,7 +19,7 @@ -
+
記事の構成について この記事は、普通の fizzbuzz @@ -28,7 +28,7 @@ にソースコードがあるので、そちらを先に見てほしい。
-
+
レギュレーション PHP で、次のような制約の下に fizzbuzz を書いた。 @@ -62,7 +62,7 @@ off になっている環境が多いようなので、今回は使わないことにした。
-
+
主な障害 1行あたりの文字数など、適当に改行を挟めばいいだけではないのか? @@ -182,541 +182,540 @@
- 標準的なインストール構成の PHP で実現できること (デフォルトで有効になっていない拡張等を使わないこと) - - -
- - に反する - (というより、「それだとおもしろくもなんともないので、このルールを足した」というのが正しい)。 - - - また、2文字だと文字列がまともに書けないのも辛い。'' だけで - 2文字使うので、「1文字の文字列リテラル」というものを書くことができない。PHP - では文字列リテラル中に生の改行が書けるので - - - - - - とすると $a"\na" になるのだが、余計な改行が入ってしまう。 - - - これらの障害をどのように乗り越えるのか、次節から見ていく。 - -
-
- 解説 -
- 普通の (?) fizzbuzz + 標準的なインストール構成の PHP で実現できること (デフォルトで有効になっていない拡張等を使わないこと) + + - まずは普通に書くとしよう。 + に反する + (というより、「それだとおもしろくもなんともないので、このルールを足した」というのが正しい)。 + + + また、2文字だと文字列がまともに書けないのも辛い。'' だけで + 2文字使うので、「1文字の文字列リテラル」というものを書くことができない。PHP + では文字列リテラル中に生の改行が書けるので - 素直に書いた fizzbuzz - とは言い難いが、このくらいは普通だということにしておかないと、この先がやっていられないので許してほしい。 + とすると $a"\na" になるのだが、余計な改行が入ってしまう。 -
-
- <literal>for</literal> の排除 - for - は、3文字もある長いキーワードである。こんなものは使えない。array_ - 系の関数を使って、適当に置き換えるとしよう。 + これらの障害をどのように乗り越えるのか、次節から見ていく。 - - +
+ 解説 +
+ 普通の (?) fizzbuzz + + まずは普通に書くとしよう。 + + + + + + 素直に書いた fizzbuzz + とは言い難いが、このくらいは普通だということにしておかないと、この先がやっていられないので許してほしい。 + +
+
+ <literal>for</literal> の排除 + + for + は、3文字もある長いキーワードである。こんなものは使えない。array_ + 系の関数を使って、適当に置き換えるとしよう。 + + + - printf((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), - ); - ]]> - - - array_walkrangeprintf といった for - よりも長いトークンが現れてしまったが、これは次節で直すことにする。なお、echo - は文 (statement) であり式 (expression) ではないので、式である printf - に置き換えた。 - + printf((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), + ); + ]]> + + + array_walkrangeprintf といった for + よりも長いトークンが現れてしまったが、これは次節で直すことにする。なお、echo + は文 (statement) であり式 (expression) ではないので、式である printf + に置き換えた。 + +
+
+ 関数呼び出しの短縮 + + rangearray_walkprintf + は長すぎるのでどうにかせねばならない。ここで、PHP + の可変関数を使う。可変関数とは、関数名が文字列として入った変数を経由して、関数を呼び出す機能である。 + + + + $p((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), + ); + ]]> + + + これで関数を呼び出している所は短くなった。では、$r$w や + $p、また 'Fizz''Buzz' はどうやって + 1行2文字に収めるのか。次のテクニックへ移ろう。 + +
+
+ 余談: PHP 8.x で動作しなくてもいいなら + + 今回使ったテクニックを説明する前に、余談として、文字列リテラルの短縮法として今回採用しなかったものを紹介する。 + +
+ + PHP 7.4〜8.1 で動作すること + +
+ + というルールがない場合、「未定義の定数が評価された場合、その定数の名前が値になる」という + PHP 7.x までの仕様が利用できる。例えば、 Fizz + という文字列が欲しければ、次のようにする。 + + + + + + こうして簡単に文字列を作れる。なお、この仕様は 7.x + 時点でも警告を受けるので、@ 演算子を使って抑制してやるとよい。 + + + + + + むしろ、このことがわかっていたからこそ PHP 8.x + での動作を要件に課したところがある。 + +
+
+ 文字列リテラルの短縮 + + 実際に使った手法の説明に移る。 + + + ずばり、文字列同士のビット演算を使う。PHP では、文字列同士でビット演算 + (&|^) + をした場合、文字列の各バイトごとに指定したビット演算がなされ、それを結合したものが演算結果となる。 + + + F]AXQ + ]]> + + + これを踏まえ、次のコードを見てみよう。 + + + + + + 実行すると、range が表示される。さて、PHP + では文字列リテラル中に生の改行を直接書いてもよいのだった + (「主な障害」の節を参照のこと)。書きかえてみよう。 + + + + + + さらに # を使って適当に調整すると、次のようになる。 + + + + + + 1行あたり2文字で、range + という文字列を生成することに成功した。他の必要な文字列にも、同様の処理をほどこす。 + + + 備考: Buzz 中にある小文字の u は、このロジックだと non-printable + な文字になってしまう。ここまでのテクニックを駆使すれば回避するのはそう難しくないので、考えてみてほしい。 + +
-
- 関数呼び出しの短縮 +
+ 完成系 - rangearray_walkprintf - は長すぎるのでどうにかせねばならない。ここで、PHP - の可変関数を使う。可変関数とは、関数名が文字列として入った変数を経由して、関数を呼び出す機能である。 + 完成したものがこちら。 - $p((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), + $x + =# + 'i + S' + ;; + $y + =' + b! + '; + $c + =# + $x + ^# + $y + ;# + $x + =# + 'x + Om + '; + $y + =' + k! + o' + ;# + $r + =# + $x + ^# + $y + ;# + $x + =# + 'k + Sk + ~} + Ma + '; + $y + =' + x! + s! + k! + '; + $w + =# + $x + ^# + $y + ;# + $x + =# + 'z + Hd + G' + ;# + $y + =' + x! + ~! + '; + $p + =# + $x + ^# + $y + ;# + $x + =# + 'L + [p + '; + $y + =' + c! + '; + $f + =# + $x + ^# + $y + ;# + $x + =# + 'H + [p + '; + $y + =' + _! + '; + $b + =# + $x + ^# + $y + ;# + $b + [1 + ]= + $c + (# + 13 + *9 + ); + $s + =# + $r + (1 + ,( + 10 + ** + 2) + ); + $w + (# + $s + ,# + fn + (# + $i + )# + => + $p + (( + (# + $i + %3 + ?# + '' + :# + $f + ). + (# + $i + %5 + ?# + '' + :# + $b + )? + :# + $i + )# + .' + ') ); ]]> +
+
+ 感想など - これで関数を呼び出している所は短くなった。では、$r$w や - $p、また 'Fizz''Buzz' はどうやって - 1行2文字に収めるのか。次のテクニックへ移ろう。 + PHP は、スクリプト言語の中だとシンタックスシュガーが少ない + (体感)。この挑戦は不可能に思われたが、PHP + マニュアルとにらめっこしていたらなんとかなった。 -
-
- 余談: PHP 8.x で動作しなくてもいいなら - 今回使ったテクニックを説明する前に、余談として、文字列リテラルの短縮法として今回採用しなかったものを紹介する。 + みんなもプログラムを細長くしよう。 -
- - PHP 7.4〜8.1 で動作すること - -
+
+
+ 余談2: 別解 - というルールがない場合、「未定義の定数が評価された場合、その定数の名前が値になる」という - PHP 7.x までの仕様が利用できる。例えば、 Fizz - という文字列が欲しければ、次のようにする。 + PHP では、バッククォートを使ってシェルを呼び出せる。これは shell_exec + 関数と等価である。さて、PHP + ではバックスラッシュによる行継続が使えないと書いたが、シェルでは使える + (当然だが、呼び出されるシェルに依存する。Bash + なら大丈夫だろう。知らんけど)。 - こうして簡単に文字列を作れる。なお、この仕様は 7.x - 時点でも警告を受けるので、@ 演算子を使って抑制してやるとよい。 + なお、ここでは簡単のため出力に printf をそのまま使っているが、実際には + printf という文字列を合成して可変関数で呼び出す。 - - - - むしろ、このことがわかっていたからこそ PHP 8.x - での動作を要件に課したところがある。 + ただし、これでは -
-
- 文字列リテラルの短縮 +
+ + スペースやタブを使用しないこと + +
- 実際に使った手法の説明に移る。 + に違反してしまう。スペースが使えないと引数とコマンドを区切れない。これは困った。 - ずばり、文字列同士のビット演算を使う。PHP では、文字列同士でビット演算 - (&|^) - をした場合、文字列の各バイトごとに指定したビット演算がなされ、それを結合したものが演算結果となる。 + もうこれ以上は不可能だと思っていたのだが、この記事の執筆中に解決する方法を思いついたので載せておく。 F]AXQ + printf(` + e\ + c\ + h\ + o\ + ${ + '_ + '} + 1\ + 2\ + 3\ + `); ]]> - これを踏まえ、次のコードを見てみよう。 + 先程と同じく、chrprintf を生成する部分は長くなるので省いた。 - + - + - 実行すると、range が表示される。さて、PHP - では文字列リテラル中に生の改行を直接書いてもよいのだった - (「主な障害」の節を参照のこと)。書きかえてみよう。 + は変数で、中にはスペースとエスケープが入っている + (chr(32) . chr(92))。シェルに渡されている文字列は次のようになる。 - + - + - さらに # を使って適当に調整すると、次のようになる。 + これは、前掲したコマンドと同じだ。かくして、スペースを陽に書かずにシェルをおおよそ自由に扱えるようになった。Fizzbuzz + のワンライナーくらいすぐ書けるだろうから、あとはなんとかなるだろう + (試してないけど)。 - - - - 1行あたり2文字で、range - という文字列を生成することに成功した。他の必要な文字列にも、同様の処理をほどこす。 + ということでこれは別解ということにしておく。 - 備考: Buzz 中にある小文字の u は、このロジックだと non-printable - な文字になってしまう。ここまでのテクニックを駆使すれば回避するのはそう難しくないので、考えてみてほしい。 + ちなみに、PHP 8.2 からは、この記法で Warning が出るようになるようだ。 + + + + + + 最新版で警告が出るというのも美しくないので、私としては本編の解法を推す。
-
-
- 完成系 - - 完成したものがこちら。 - - - - $p - (( - (# - $i - %3 - ?# - '' - :# - $f - ). - (# - $i - %5 - ?# - '' - :# - $b - )? - :# - $i - )# - .' - ') - ); - ]]> - -
-
- 感想など - - PHP は、スクリプト言語の中だとシンタックスシュガーが少ない - (体感)。この挑戦は不可能に思われたが、PHP - マニュアルとにらめっこしていたらなんとかなった。 - - - みんなもプログラムを細長くしよう。 - -
-
- 余談2: 別解 - - PHP では、バッククォートを使ってシェルを呼び出せる。これは shell_exec - 関数と等価である。さて、PHP - ではバックスラッシュによる行継続が使えないと書いたが、シェルでは使える - (当然だが、呼び出されるシェルに依存する。Bash - なら大丈夫だろう。知らんけど)。 - - - - - - なお、ここでは簡単のため出力に printf をそのまま使っているが、実際には - printf という文字列を合成して可変関数で呼び出す。 - - - ただし、これでは - -
- - スペースやタブを使用しないこと - -
- - に違反してしまう。スペースが使えないと引数とコマンドを区切れない。これは困った。 - - - もうこれ以上は不可能だと思っていたのだが、この記事の執筆中に解決する方法を思いついたので載せておく。 - - - - - - 先程と同じく、chrprintf を生成する部分は長くなるので省いた。 - - - - - - は変数で、中にはスペースとエスケープが入っている - (chr(32) . chr(92))。シェルに渡されている文字列は次のようになる。 - - - - - - これは、前掲したコマンドと同じだ。かくして、スペースを陽に書かずにシェルをおおよそ自由に扱えるようになった。Fizzbuzz - のワンライナーくらいすぐ書けるだろうから、あとはなんとかなるだろう - (試してないけど)。 - - - ということでこれは別解ということにしておく。 - - - ちなみに、PHP 8.2 からは、この記法で Warning が出るようになるようだ。 - - - - - - 最新版で警告が出るというのも美しくないので、私としては本編の解法を推す。 - -
diff --git a/public/posts/2021-03-30/phperkaigi-2021/index.html b/public/posts/2021-03-30/phperkaigi-2021/index.html index 2e7df8c..172f83a 100644 --- a/public/posts/2021-03-30/phperkaigi-2021/index.html +++ b/public/posts/2021-03-30/phperkaigi-2021/index.html @@ -59,8 +59,8 @@
-
-

PHPerKaigi 2021 参加レポ

+
+

PHPerKaigi 2021 参加レポ

2021-03-26 から 2021-03-28 にかけて開催された、 PHPerKaigi 2021 に一般参加者として参加した。 弊社 デジタルサーカス株式会社 (今年1月から勤務) はダイヤモンドスポンサーとなっており、スポンサー枠のチケットを使わせていただいた。

@@ -73,8 +73,8 @@ 発表はトラック A、B に分かれていたのだが、今回はすべて A トラックを視聴している (切り替えるのが面倒だっただけ)。

-
-

凡例

+
+

凡例

発表・スライドのメモ (引用ではない) @@ -86,10 +86,10 @@

-
-

Day 0 前夜祭 (2021/03/27)

-
-

17:30 [A]

+
+

Day 0 前夜祭 (2021/03/27)

+
+

17:30 [A]

PHP で AWS Lambda

@@ -155,8 +155,8 @@

-
-

18:10 [A]

+
+

18:10 [A]

大規模サイトの SEO

@@ -222,8 +222,8 @@

-
-

18:50 [A]

+
+

18:50 [A]

知覚可能 操作可能 理解可能 堅牢 ちゃんとしたHTMLを書く (閉じタグ・入れ子構造など) @@ -314,8 +314,8 @@

-
-

19:30 [A]

+
+

19:30 [A]

PHP で FUSE

@@ -406,10 +406,10 @@
-
-

Day 1 (2021/03/27)

-
-

10:50 [A]

+
+

Day 1 (2021/03/27)

+
+

10:50 [A]

ATDD

@@ -556,8 +556,8 @@

-
-

11:50 [A]

+
+

11:50 [A]

型解析を用いたリファクタリング

@@ -611,15 +611,15 @@

-
-

12:30 [A]

+
+

12:30 [A]

昼食をとっていた。事前に何か食料を買っておくべきだった。

-
-

13:10 [A]

+
+

13:10 [A]

Documentation as Code

@@ -691,8 +691,8 @@

-
-

14:10 [A]

+
+

14:10 [A]

cookie による session 管理

@@ -702,8 +702,8 @@

-
-

14:50 [A]

+
+

14:50 [A]

PHP のエラーと例外

@@ -842,8 +842,8 @@

-
-

15:30 [A]

+
+

15:30 [A]

Laravel のメール認証

@@ -853,8 +853,8 @@

-
-

16:10 [A]

+
+

16:10 [A]

gRPC

@@ -918,8 +918,8 @@

-
-

16:50 [A]

+
+

16:50 [A]

アーキテクチャテスト

@@ -978,8 +978,8 @@
-
-

Day 2 (2021/03/28)

+
+

Day 2 (2021/03/28)

冒頭に書いた通り、2日目から体調が悪くまともに聴けていない。途中までは頭痛を我慢しつつ見ていたのだが、まともに入ってこなかった。

@@ -989,8 +989,8 @@

-
-

全体の感想

+
+

全体の感想

Day 2 にほとんど参加できなかったのは残念だが、イベント自体は大変楽しく、また興味深いものであった。自分がまったく知らない領域の話を聞けるのはこうしたイベントならではだと感じる。オンライン開催ゆえ現地に行く必要がなく、気軽に参加できたのも (特に初参加者として) 嬉しいポイントだった。

diff --git a/public/posts/2021-10-02/ruby-then-keyword-and-case-in/index.html b/public/posts/2021-10-02/ruby-then-keyword-and-case-in/index.html index 097d417..ba31a99 100644 --- a/public/posts/2021-10-02/ruby-then-keyword-and-case-in/index.html +++ b/public/posts/2021-10-02/ruby-then-keyword-and-case-in/index.html @@ -65,15 +65,15 @@

-
-

TL; DR

+
+

TL; DR

case - in によるパターンマッチング構文でも、case - when と同じように then が使える (場合によっては使う必要がある)。

-
-

then とは

+
+

then とは

使われることは稀だが、Ruby では then がキーワードになっている。次のように使う:

@@ -110,8 +110,8 @@ end
-
-

なぜ普段は書かなくてもよいのか

+
+

なぜ普段は書かなくてもよいのか

普通 Ruby のコードで then を書くことはない。なぜか。次のコードを実行してみるとわかる。

@@ -144,8 +144,8 @@ puts 'Hello, World!' -

なぜ then; や改行が必要か

+
+

なぜ then; や改行が必要か

なぜ then; や改行 (以下 「then 等」) が必要なのだろうか。次の例を見てほしい:

@@ -175,8 +175,8 @@ b

-
-

case - in における then

+
+

case - in における then

ようやく本題にたどり着いた。来る Ruby 3.0 では casein キーワードを使ったパターンマッチングの構文が入る予定である。この構文でもパターン部との区切りとして then 等が必要になる。 (現在の) Ruby には formal な形式での文法仕様は存在しないので、yacc の定義ファイルを参照した (yacc の説明は省略)。

@@ -259,8 +259,8 @@ p_cases end
-
-

まとめ

+
+

まとめ

  • ifcase の条件の後ろには then;、改行のいずれかが必要 diff --git a/public/posts/2021-10-02/rust-where-are-primitive-types-from/index.html b/public/posts/2021-10-02/rust-where-are-primitive-types-from/index.html index 9e77a85..8c6e269 100644 --- a/public/posts/2021-10-02/rust-where-are-primitive-types-from/index.html +++ b/public/posts/2021-10-02/rust-where-are-primitive-types-from/index.html @@ -62,8 +62,8 @@

    -
    -

    前置き

    +
    +

    前置き

    Rust において、プリミティブ型の名前は予約語でない。したがって、次のコードは合法である。

    @@ -100,8 +100,8 @@
    -
    -

    調査

    +
    +

    調査

    調査に使用したソース (調査時点での最新 master)

    @@ -242,8 +242,8 @@ rustc_resolve/src/lib.rs: table.insert(sym::i128, Int(IntTy::I128));

    -
    -

    まとめ

    +
    +

    まとめ

    Rust のプリミティブ型は予約語ではない。名前解決の最終段階で特別扱いされ、他に同名の型が見つかっていなければ対応するプリミティブ型に解決される。

    diff --git a/public/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre/index.html b/public/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre/index.html index 44ee689..b9455f7 100644 --- a/public/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre/index.html +++ b/public/posts/2021-10-02/vim-difference-between-autocmd-bufwrite-and-bufwritepre/index.html @@ -62,15 +62,15 @@

    -
    -

    TL; DR

    +
    +

    TL; DR

    違いはない。ただのエイリアス。

    -
    -

    調査記録

    +
    +

    調査記録

    Vim の autocmd events には似通った名前のものがいくつかある。大抵は :help に説明があるが、この記事のタイトルにある2つを含めた以下のイベントには、その違いについて説明がない。

    @@ -109,8 +109,8 @@

    -
    -

    vim のソースコード

    +
    +

    vim のソースコード

    以下は、autocmd events の名前と内部で使われている整数値とのマッピングを定義している箇所である。見ての通り、上でエイリアスではないかと述べた3組には、それぞれ同じ内部値が使われている。

    @@ -139,8 +139,8 @@ {"BufWritePre", EVENT_BUFWRITEPRE},
    -
    -

    neovim のソースコード

    +
    +

    neovim のソースコード

    neovim の場合でも同様のマッピングが定義されているが、こちらの場合は Lua で書かれている。以下にある通り、はっきり aliases と書かれている。

    @@ -160,59 +160,59 @@ FileEncoding = 'EncodingChanged', ところで、上では取り上げなかった FileEncoding だが、これは :help FileEncoding にしっかりと書いてある。

    -
                                                               *FileEncoding*
    -  FileEncoding                    Obsolete.  It still works and is equivalent
    +              
                                                                  *FileEncoding*
    +FileEncoding                    Obsolete.  It still works and is equivalent
                                     to |EncodingChanged|.
    +
    + +
    +

    まとめ

    +

    + 記事タイトルについて言えば、どちらも変わらないので好きな方を使えばよい。あえて言えば、次のようになるだろう。 +

    -
    -

    まとめ

    -

    - 記事タイトルについて言えば、どちらも変わらないので好きな方を使えばよい。あえて言えば、次のようになるだろう。 -

    +
      +
    • + BufAdd/BufCreate +
        +
      • + → BufCreate は歴史的な理由により ("for historic reasons") 存在しているため、新しい方 (BufAdd) を使う +
      • +
      +
    • -
        -
      • - BufAdd/BufCreate -
          -
        • - → BufCreate は歴史的な理由により ("for historic reasons") 存在しているため、新しい方 (BufAdd) を使う -
        • -
        -
      • - -
      • - BufRead/BufReadPost -
          -
        • - → BufReadPre との対称性のため、あるいは BufWritePost との対称性のため BufReadPost を使う -
        • -
        -
      • - -
      • - BufWrite/BufWritePre -
          -
        • - → BufWritePost との対称性のため、あるいは BufReadPre との対称性のため BufWritePre を使う -
        • -
        -
      • - -
      • - FileEncoding/EncodingChanged -
          -
        • - → FileEncoding`Obsolete'' と明言されているので、`EncodingChanged を使う -
        • -
        -
      • -
      +
    • + BufRead/BufReadPost +
        +
      • + → BufReadPre との対称性のため、あるいは BufWritePost との対称性のため BufReadPost を使う +
      • +
      +
    • -

      - ところでこの調査で知ったのだが、BufReadBufWrite は上にある通り発火するタイミングが「後」と「前」で対称性がない。可能なら Pre/Post 付きのものを使った方が分かりやすいだろう。 -

      -
    +
  • + BufWrite/BufWritePre +
      +
    • + → BufWritePost との対称性のため、あるいは BufReadPre との対称性のため BufWritePre を使う +
    • +
    +
  • + +
  • + FileEncoding/EncodingChanged +
      +
    • + → FileEncoding`Obsolete'' と明言されているので、`EncodingChanged を使う +
    • +
    +
  • +
+ +

+ ところでこの調査で知ったのだが、BufReadBufWrite は上にある通り発火するタイミングが「後」と「前」で対称性がない。可能なら Pre/Post 付きのものを使った方が分かりやすいだろう。 +

diff --git a/public/posts/2021-10-02/vim-swap-order-of-selected-lines/index.html b/public/posts/2021-10-02/vim-swap-order-of-selected-lines/index.html index 6b9e423..320e80e 100644 --- a/public/posts/2021-10-02/vim-swap-order-of-selected-lines/index.html +++ b/public/posts/2021-10-02/vim-swap-order-of-selected-lines/index.html @@ -62,8 +62,17 @@

-
-

バージョン情報

+
+

TL; DR

+
" License: Public Domain
+
+command! -bar -range=%
+    \ Reverse
+    \ keeppatterns <line1>,<line2>g/^/m<line1>-1
+
+ +
+

バージョン情報

:version の一部

@@ -75,10 +84,10 @@
-
-

よく紹介されている手法

-
-

tac / tail

+
+

よく紹介されている手法

+
+

tac / tail

tactail -r などの外部コマンドを ! を使って呼び出し、置き換える。

@@ -94,8 +103,8 @@

-
-

:g/^/m0

+
+

:g/^/m0

こちらは外部コマンドに頼らず、Vim の機能のみを使う。g:global コマンドの、m:move コマンドの略

@@ -138,8 +147,8 @@
-
-

:g/^/m0 の問題点

+
+

:g/^/m0 の問題点

:global コマンドは各行に対してマッチングを行う際、現在の検索パターンを上書きしてしまう。^ は行の先頭にマッチするため、結果として全ての行がハイライトされてしまう。'hlsearch' オプションを無効にしている場合その限りではないが、その場合でも直前の検索パターンが失われてしまうと n コマンドなどの際に不便である。

@@ -151,8 +160,8 @@
-
-

解決策

+
+

解決策

[2020/9/28追記] より簡潔な方法を見つけたので次節に追記した @@ -212,8 +221,8 @@ command! -bar -range=%

-
-

解決策 (改訂版)

+
+

解決策 (改訂版)

[2020/9/28追記] より簡潔な方法を見つけたため追記する @@ -234,15 +243,6 @@ command! -bar -range=%

- -
-

コピペ用再掲

-
" License: Public Domain
-
-command! -bar -range=%
-    \ Reverse
-    \ keeppatterns <line1>,<line2>g/^/m<line1>-1
-
diff --git a/public/posts/2022-04-09/phperkaigi-2022-tokens/index.html b/public/posts/2022-04-09/phperkaigi-2022-tokens/index.html index d834bb8..518e744 100644 --- a/public/posts/2022-04-09/phperkaigi-2022-tokens/index.html +++ b/public/posts/2022-04-09/phperkaigi-2022-tokens/index.html @@ -73,8 +73,8 @@

-
-

第1問 brainf_ck.php

+
+

第1問 brainf_ck.php

ソースコードはこちら。実行には PHP 8.1 以上が必要なので注意。

@@ -153,17 +153,17 @@ $🐘([ この問題は、単に適切なバージョンの PHP で動かせばトークンが得られる。

-
-

解説

-
-

絵文字

+
+

解説

+
+

絵文字

まず目につくのは大量の絵文字だろう。 PHP は識別子に使用できる文字の範囲が広く、絵文字も使うことができる。

-
-

プログラム全体

+
+

プログラム全体

Brainf*ck のインタプリタとプログラムになっている。 Brainf*ck とは、難解プログラミング言語のひとつであり、ここで説明するよりも Wikipedia の該当ページを読んだ方がよい。

@@ -246,22 +246,22 @@ $🐘([

-
-

絵文字の選択

+
+

絵文字の選択

おおよそ意味に合致するよう選んでいるが、$🤡$🎪 は弊社デジタルサーカスにちなんでいる。 また、$🐘 は PHP のマスコットの象に由来する。

-
-

strict_types

+
+

strict_types

declare 文の strict_types に指定できるのは、01 の数値リテラルだが、 0x00b1 のような値も受け付ける。 今回は、PHP 8.1 から追加された、0O または 0o から始まる八進数リテラルを使った。

-
-

URL

+
+

URL

ソースコードのライセンスを示したこの部分だが、

@@ -273,8 +273,8 @@ $🐘([

-
-

リテラルなしで数値を生成する

+
+

リテラルなしで数値を生成する

ソースコード中に、ほとんど数値リテラルが書かれていないことにお気づきだろうか。 PHP では、型変換を利用することで任意の整数を作り出すことができる。

@@ -294,15 +294,15 @@ $🐘([

-
-

if 文なしで条件分岐

+
+

if 文なしで条件分岐

三項演算子ないし match 式を使うことで、if を一切書かずに条件分岐ができる。 また、&& / || も使えることがある。 遅延評価が不要なケースでは、[$t, $f][$cond] のような形で分岐することもできる。

-
-

whilefor 文なしでループ

+
+

whilefor 文なしでループ

不動点コンビネータを使って無名再帰する (詳しい説明は省略する。これらの単語で検索してほしい)。 ここでは、一般に Z コンビネータとして知られるものを使った ($z)。

@@ -318,8 +318,8 @@ $🐘([
-
-

第2問 riddle.php

+
+

第2問 riddle.php

ソースコードはこちら。実行には PHP 8.0 以上が必要なので注意。

@@ -367,8 +367,8 @@ $🐘([ ここでは、私の想定解を解説する。

-
-

読解

+
+

読解

まずはソースコードを読んでいく。

@@ -406,8 +406,8 @@ $🐘([

-
-

ヒント

+
+

ヒント

次に、ソースコードに書いてあるヒントを読んでいく。

@@ -435,8 +435,8 @@ $🐘([

-
-

解く

+
+

解く

ここまでわかれば、あと一歩で解ける。すなわち、0x14B499C# に変換されるような N を見つければよい。

@@ -495,8 +495,8 @@ $🐘([
-
-

第3問 toquine.php

+
+

第3問 toquine.php

ソースコードはこちら。

@@ -541,10 +541,10 @@ Q; 実際にはもう少しパイプで繋げなければならない。

-
-

解説

-
-

プログラム全体

+
+

解説

+
+

プログラム全体

コメントにもあるとおり、これは quine (風) のプログラムになっている。 Quine とは、自分のソースコードをそっくりそのまま出力するようなプログラムのことである。

@@ -554,22 +554,22 @@ Q;

-
-

トークン

+
+

トークン

$xs がトークンに対応している。変換のロジックは riddle.php とほぼ同じなので省略する。

-
-

状態保持

+
+

状態保持

トークンの何文字目まで出力したかを、ソースコードを変えずに (quine なので) 覚えておく必要がある。 このプログラムでは、トークンが出力されるとソースコードがだんだんと長くなっていくのを利用して、LINE から情報を取得している。

-
-

ROT 13

+
+

ROT 13

Quine は、素朴に書くとプログラムの一部が 2回記述されてしまう。 これがあまり美しくないので、toquine.php では、ROT 13 変換を使って難読化した。

diff --git a/public/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal/index.html b/public/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal/index.html index cd997f7..4475dc5 100644 --- a/public/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal/index.html +++ b/public/posts/2022-04-24/term-banner-write-tool-showing-banner-in-terminal/index.html @@ -71,8 +71,8 @@

-
-

Motivation

+
+

Motivation

以前、https://github.com/nsfisis/big-clock-mode[big-clock-mode] という似たようなプログラムを書いた。 これは tmux の :clock-mode コマンドに着想を得たもので、:clock-mode よりも大きく現在時刻を表示する。

@@ -94,8 +94,8 @@

-
-

プログラム

+
+

プログラム

全体の流れは次のようになっている。

@@ -123,8 +123,8 @@

-
-

フォント

+
+

フォント

フリーの 8x8 ビットマップフォントである、https://littlelimit.net/misaki.htm[美咲フォント 2021-05-05a 版] を使わせていただいた。

diff --git a/public/posts/2022-05-01/phperkaigi-2022/index.html b/public/posts/2022-05-01/phperkaigi-2022/index.html index f4c89fa..df97547 100644 --- a/public/posts/2022-05-01/phperkaigi-2022/index.html +++ b/public/posts/2022-05-01/phperkaigi-2022/index.html @@ -70,10 +70,10 @@

-
-

感想

-
-

厳選おすすめトーク

+
+

感想

+
+

厳選おすすめトーク

多くの素晴らしいトークの中から、特におすすめのものを 5つ選んだ。是非聞いてほしい。引用部分は、リンク先プロポーザルから引用している。

@@ -175,15 +175,15 @@
-
-

トークン問題の作成

+
+

トークン問題の作成

今回は、PHPer チャレンジ用に弊社のトークン問題を 3題作成した。こちらについては別途記事にしているので、そちらを参照されたい。

-
-

PHPer チャレンジ

+
+

PHPer チャレンジ

1位になった。
@@ -191,8 +191,8 @@

-
-

カンファレンス全体への感想

+
+

カンファレンス全体への感想

去年の参加レポ では、こんなことを書いた。

@@ -221,8 +221,8 @@
-
-

そして来年へ……?

+
+

そして来年へ……?

PHPerKaigi 2023 があるかどうか存じ上げないが、あるとすれば、次の 4つを目標としたい。

diff --git a/public/posts/2022-08-27/php-conference-okinawa-code-golf/index.html b/public/posts/2022-08-27/php-conference-okinawa-code-golf/index.html index 0fb3911..6aa732d 100644 --- a/public/posts/2022-08-27/php-conference-okinawa-code-golf/index.html +++ b/public/posts/2022-08-27/php-conference-okinawa-code-golf/index.html @@ -76,8 +76,8 @@

-
-

+
+

細かいレギュレーションは不明だったので、勝手に定めた。

@@ -133,24 +133,24 @@ ?>]
-
-

使用したテクニック

-
-

指数表記

+
+

使用したテクニック

+
+

指数表記

割と多くの言語のゴルフで使えるテクニック。e を用いた指数表記で、大きな数を短く表す。このコードでは 10000500020001000 を指数表記している。

-
-

foreach や for の中身を1つの文に

+
+

foreach や for の中身を1つの文に

foreachforif などの後ろには、通常 { を続けて複数の文を連ねるが、中身の文を1つにしてしまえば、{} を省略できる。C言語などでも使える。

-
-

$r に初期値を入れない

+
+

$r に初期値を入れない

PHP では、$r[] = &#8230;&#8203; のような配列の末尾に追加する式を実行したとき、$r が未定義だった場合は $r を勝手に定義して空の配列で初期化してくれる。これを利用すると、$r = []; のような初期化が不要になる。

@@ -164,8 +164,8 @@

-
-

PHP タグの外に文字列を置く

+
+

PHP タグの外に文字列を置く

PHP では、<?php ?> で囲われた部分の外側にある文字列は、そのまま出力される。今回のケースでは、先頭と末尾に必ず [] を出力するので、そのまま書いてやればよい。

diff --git a/public/posts/2022-08-31/support-for-communty-is-employee-benefits/index.html b/public/posts/2022-08-31/support-for-communty-is-employee-benefits/index.html index 30c0019..fec8f70 100644 --- a/public/posts/2022-08-31/support-for-communty-is-employee-benefits/index.html +++ b/public/posts/2022-08-31/support-for-communty-is-employee-benefits/index.html @@ -66,8 +66,8 @@

-
-

なぜ?

+
+

なぜ?

組織としての寄付理由は前掲した記事に譲るとして、ここでは、私が社内でこの件を推進した理由について書くことにします。

diff --git a/public/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line/index.html b/public/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line/index.html index 23028a3..c0ae51e 100644 --- a/public/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line/index.html +++ b/public/posts/2022-09-29/write-fizzbuzz-in-php-2-letters-per-line/index.html @@ -56,15 +56,15 @@
-
-

記事の構成について

+
+

記事の構成について

この記事は、普通の fizzbuzz を徐々に変形して最終形にしていく、という構成で書かれている。最終形を見てどのような仕組みで動いているのか解読してから解説を読みたい、というかたがいれば、 このページ にソースコードがあるので、そちらを先に見てほしい。

-
-

レギュレーション

+
+

レギュレーション

PHP で、次のような制約の下に fizzbuzz を書いた。

@@ -110,8 +110,8 @@

-
-

主な障害

+
+

主な障害

1行あたりの文字数など、適当に改行を挟めばいいだけではないのか?

@@ -232,7 +232,7 @@ c\
  • - 標準的なインストール構成の PHP で実現できること (デフォルトで有効になっていない拡張等を使わないこと) + 標準的なインストール構成の PHP で実現できること (デフォルトで有効になっていない拡張等を使わないこと)
@@ -259,10 +259,10 @@ a'

-
-

解説

-
-

普通の (?) fizzbuzz

+
+

解説

+
+

普通の (?) fizzbuzz

まずは普通に書くとしよう。

@@ -278,8 +278,8 @@ a'

-
-

for の排除

+
+

for の排除

for は、3文字もある長いキーワードである。こんなものは使えない。array_ 系の関数を使って、適当に置き換えるとしよう。

@@ -288,9 +288,9 @@ a' $s = range(1, 100); array_walk( - $s, - fn($i) => - printf((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), +$s, +fn($i) => +printf((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), );

@@ -298,8 +298,8 @@ a'

-
-

関数呼び出しの短縮

+
+

関数呼び出しの短縮

rangearray_walkprintf は長すぎるのでどうにかせねばならない。ここで、PHP の可変関数を使う。可変関数とは、関数名が文字列として入った変数を経由して、関数を呼び出す機能である。

@@ -312,9 +312,9 @@ a' $s = $r(1, 100); $w( - $s, - fn($i) => - $p((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), +$s, +fn($i) => +$p((($i % 3 ? '' : 'Fizz') . ($i % 5 ? '' : 'Buzz') ?: $i) . "\n"), );

@@ -322,8 +322,8 @@ a'

-
-

余談: PHP 8.x で動作しなくてもいいなら

+
+

余談: PHP 8.x で動作しなくてもいいなら

今回使ったテクニックを説明する前に、余談として、文字列リテラルの短縮法として今回採用しなかったものを紹介する。

@@ -366,8 +366,8 @@ F.

-
-

文字列リテラルの短縮

+
+

文字列リテラルの短縮

実際に使った手法の説明に移る。

@@ -382,7 +382,7 @@ F. // $a ^ $b は次のコードと同じ $result = ''; for ($i = 0; $i < min(strlen($a), strlen($b)); $i++) { - $result .= $a[$i] ^ $b[$i]; +$result .= $a[$i] ^ $b[$i]; } echo $result; @@ -447,8 +447,8 @@ o'
-
-

完成系

+
+

完成系

完成したものがこちら。

@@ -604,8 +604,8 @@ _! );
-
-

感想など

+
+

感想など

PHP は、スクリプト言語の中だとシンタックスシュガーが少ない (体感)。この挑戦は不可能に思われたが、PHP マニュアルとにらめっこしていたらなんとかなった。

@@ -615,8 +615,8 @@ _!

-
-

余談2: 別解

+
+

余談2: 別解

PHP では、バッククォートを使ってシェルを呼び出せる。これは shell_exec 関数と等価である。さて、PHP ではバックスラッシュによる行継続が使えないと書いたが、シェルでは使える (当然だが、呼び出されるシェルに依存する。Bash なら大丈夫だろう。知らんけど)。

-- cgit v1.2.3-70-g09d2