aboutsummaryrefslogtreecommitdiffhomepage
path: root/services/nuldoc/content/posts/2022-04-09
diff options
context:
space:
mode:
authornsfisis <nsfisis@gmail.com>2025-11-27 05:05:04 +0900
committernsfisis <nsfisis@gmail.com>2025-11-27 06:07:46 +0900
commitc754d24b162ecd504f3c4bdd8632045dd0398768 (patch)
tree362323710bb329ad609d379df4e4a429e4229fd2 /services/nuldoc/content/posts/2022-04-09
parentd1014de68415df8f0a5dc3389332e086119c6198 (diff)
downloadnsfisis.dev-c754d24b162ecd504f3c4bdd8632045dd0398768.tar.gz
nsfisis.dev-c754d24b162ecd504f3c4bdd8632045dd0398768.tar.zst
nsfisis.dev-c754d24b162ecd504f3c4bdd8632045dd0398768.zip
feat(nuldoc): Djot to Markdown
Diffstat (limited to 'services/nuldoc/content/posts/2022-04-09')
-rw-r--r--services/nuldoc/content/posts/2022-04-09/phperkaigi-2022-tokens.md (renamed from services/nuldoc/content/posts/2022-04-09/phperkaigi-2022-tokens.dj)75
1 files changed, 25 insertions, 50 deletions
diff --git a/services/nuldoc/content/posts/2022-04-09/phperkaigi-2022-tokens.dj b/services/nuldoc/content/posts/2022-04-09/phperkaigi-2022-tokens.md
index 3956583..e5f5541 100644
--- a/services/nuldoc/content/posts/2022-04-09/phperkaigi-2022-tokens.dj
+++ b/services/nuldoc/content/posts/2022-04-09/phperkaigi-2022-tokens.md
@@ -17,8 +17,7 @@ remark = "公開"
date = "2022-04-16"
remark = "2問目、3問目の解説を追加、1問目に加筆"
---
-{#intro}
-# はじめに
+# はじめに {#intro}
本日開始された [PHPerKaigi 2022](https://phperkaigi.jp/2022/) の PHPer
チャレンジにおいて、弊社
@@ -27,13 +26,11 @@ remark = "2問目、3問目の解説を追加、1問目に加筆"
リポジトリはこちら: https://github.com/nsfisis/PHPerKaigi2022-tokens
-{#q1-brainfuck}
-# 第1問 brainf_ck.php
+# 第1問 brainf_ck.php {#q1-brainfuck}
ソースコードはこちら。実行には PHP 8.1 以上が必要なので注意。
-{filename="brainf_ck.php"}
-```php
+```php filename="brainf_ck.php"
<?php
declare(strict_types=0O1);
@@ -107,17 +104,14 @@ $🐘([
この問題は、単に適切なバージョンの PHP で動かせばトークンが得られる。
-{#commentary}
-## 解説
+## 解説 {#commentary}
-{#emoji}
-### 絵文字
+### 絵文字 {#emoji}
まず目につくのは大量の絵文字だろう。 PHP
は識別子に使用できる文字の範囲が広く、絵文字も使うことができる。
-{#brainfuck}
-### プログラム全体
+### プログラム全体 {#brainfuck}
Brainf\*ck のインタプリタとプログラムになっている。 Brainf\*ck
とは、難解プログラミング言語のひとつであり、ここで説明するよりも
@@ -169,22 +163,19 @@ https://ja.wikipedia.org/wiki/Brainfuck
なお、`$🐘` はいわゆる main 関数であり、プログラムの実行部分である。
-{#emoji-selection}
-### 絵文字の選択
+### 絵文字の選択 {#emoji-selection}
おおよそ意味に合致するよう選んでいるが、`$🤡` と `$🎪`
は弊社デジタルサーカスにちなんでいる。 また、`$🐘` は PHP
のマスコットの象に由来する。
-{#strict-types}
-### strict_types
+### strict_types {#strict-types}
`declare` 文の `strict_types` に指定できるのは、`0` か `1`
の数値リテラルだが、 `0x0` や `0b1` のような値も受け付ける。 今回は、PHP
8.1 から追加された、`0O` または `0o` から始まる八進数リテラルを使った。
-{#url}
-### URL
+### URL {#url}
ソースコードのライセンスを示したこの部分だが、
@@ -195,8 +186,7 @@ https://creativecommons.org/publicdomain/zero/1.0/
完全に合法な PHP のコードである。 `https:` 部分はラベル、`//`
以降は行コメントになっている。
-{#numbers}
-### リテラルなしで数値を生成する
+### リテラルなしで数値を生成する {#numbers}
ソースコード中に、ほとんど数値リテラルが書かれていないことにお気づきだろうか。
PHP では、型変換を利用することで任意の整数を作り出すことができる。
@@ -220,16 +210,14 @@ assert(10 === +(![].+!![]));
によって文字列を `false` にし、`+` によって `false` を `0`
にし、さらにビット反転して `-1` にしている。
-{#conditionals}
-### `if` 文なしで条件分岐
+### `if` 文なしで条件分岐 {#conditionals}
三項演算子ないし `match` 式を使うことで、`if`
を一切書かずに条件分岐ができる。 また、`&amp;&amp;` / `||` も使えることがある。
遅延評価が不要なケースでは、`[$t, $f][$cond]`
のような形で分岐することもできる。
-{#loops}
-### `while`、`for` 文なしでループ
+### `while`、`for` 文なしでループ {#loops}
不動点コンビネータを使って無名再帰する
(詳しい説明は省略する。これらの単語で検索してほしい)。 ここでは、一般に
@@ -242,13 +230,11 @@ Z コンビネータとして知られるものを使った (`$z`)。
ので、 あまりに長い brainf*ck
プログラムを書くとスタックオーバーフローする。
-{#q2-riddle}
-# 第2問 riddle.php
+# 第2問 riddle.php {#q2-riddle}
ソースコードはこちら。実行には PHP 8.0 以上が必要なので注意。
-{filename="riddle.php"}
-```php
+```php filename="riddle.php"
<?php
/*********************************************************
@@ -291,8 +277,7 @@ foreach ($token as $x) {
ここでは、私の想定解を解説する。
-{#code-reading}
-## 読解
+## 読解 {#code-reading}
まずはソースコードを読んでいく。
@@ -328,8 +313,7 @@ $x = implode("\n", str_split($x, length: 5));
5文字ごとに区切ったあと、改行で結合している。
-{#hint}
-## ヒント
+## ヒント {#hint}
次に、ソースコードに書いてあるヒントを読んでいく。
@@ -343,8 +327,7 @@ $x = implode("\n", str_split($x, length: 5));
になるのではないかと予想される (なお、このことは、リポジトリの README
ファイルに追加ヒントとして書かれている)。
-{#solve}
-## 解く
+## 解く {#solve}
ここまでわかれば、あと一歩で解ける。すなわち、`0x14B499C` が `#`
に変換されるような `N` を見つければよい。
@@ -399,13 +382,11 @@ echo "N = $n\n";
これを実行すると、`N` が得られる。
-{#q3-toquine}
-# 第3問 toquine.php
+# 第3問 toquine.php {#q3-toquine}
ソースコードはこちら。
-{filename="toquine.php"}
-```php
+```php filename="toquine.php"
<?php
// License: https://creativecommons.org/publicdomain/zero/1.0/
@@ -445,11 +426,9 @@ $ php toquine.php | php | php | php | ...
実際にはもう少しパイプで繋げなければならない。
-{#commentary}
-## 解説
+## 解説 {#commentary}
-{#quine}
-### プログラム全体
+### プログラム全体 {#quine}
コメントにもあるとおり、これは quine (風) のプログラムになっている。
Quine
@@ -458,22 +437,19 @@ Quine
このプログラムは、実行すると自身とほとんど同じプログラムを出力する。
異なるのはトークンになっている部分のみである。
-{#tokens}
-### トークン
+### トークン {#tokens}
`$xs` がトークンに対応している。変換のロジックは `riddle.php`
とほぼ同じなので省略する。
-{#states}
-### 状態保持
+### 状態保持 {#states}
トークンの何文字目まで出力したかを、ソースコードを変えずに (quine
なので) 覚えておく必要がある。
このプログラムでは、トークンが出力されるとソースコードがだんだんと長くなっていくのを利用して、`__LINE__`
から情報を取得している。
-{#rot-13}
-### ROT 13
+### ROT 13 {#rot-13}
Quine は、素朴に書くとプログラムの一部が 2回記述されてしまう。
これがあまり美しくないので、`toquine.php` では、ROT 13
@@ -481,8 +457,7 @@ Quine は、素朴に書くとプログラムの一部が 2回記述されてし
それにしてもなぜこんなものが標準ライブラリに……。
-{#outro}
-# おわりに
+# おわりに {#outro}
解いていただいたみなさん、また、難易度調整につきあっていただいた社内のみなさん、ありがとうございました。