こもろぐ @tenkoma

What We Find Changes Who We Become -- Peter Morville著『アンビエント・ファインダビリティ 』

CHROMEのAVAIL BACKPACKを買った

https://www.chromeindustries.jp/smartphone/detail.html?id=000000000632

2014年にcote&ciel のリュックを買って使ってましたが、底が破れたり、肩のベルトがどんどんずれて背負い心地が悪くかったので買い換えようと。 以前CHROMEのメッセンジャーバッグを使っててよかったのでまたCHROMEに。

肩紐が全くズレないし、背中が暑くならないのでウォーキングが快適です。 ショップでは15インチノートPCが入るかは書いてありませんでしたが、 Macbook Pro 15インチがちょうど入る大きさでした。 電車で立つ時に、前に抱えるのも楽。 良い買い物をしたと思います。

PHPカンファレンス福岡2019 マネクラからの挑戦状 Webサイトコードゴルフ スコア60230(非公認)の解説

PHPカンファレンス福岡2019内企画 マネクラからの挑戦状、開催時間内にはほとんどやってませんでしたが、後日やってみて、スコア60230を出せたので解説してみます。開催時間外なので非公認スコアです。

(記事公開後、 @m3m0r7)さんと相談しながら縮めた結果、60300→60230へとさらに70短縮できました。

PHPカンファレンス福岡2019 マネクラからの挑戦状 Webサイトコードゴルフ

スコア60230(PHPファイル(480文字)+画像ファイル)

まずは入念にレギュレーションをチェック

プログラム一式をマネージドクラウドインスタンスにデプロイ後、オンライン上に用意されたDiffツールを使って、ブラウザレンダリング結果が一致しているかチェックします。合格したら、make check コマンドでスコアを計測する、という流れです。また以下のレギュレーションが存在します。

  • PHPで作成されたサイト https://phpconfuk-codegolf-php.lolipop.io/ (正解サイト)のソースコードをお渡しします(このリポジトリです)。
  • サイトの 表示を一切変えずに Webサイトを構成する全コード全ファイルの合計ファイルサイズを小さくして、あなたのロリポップ!マネージドクラウドPHPプロジェクト にデプロイしてください。
  • 最も小さいファイルサイズになった人が優勝です
  • コンテナ内の /var/www/html 内にWebサイトを表示するのに必要な全てのコード、およびファイルを設置してください
    • /var/www 等への設置は禁止です
  • Makefile内の check タスク内のコマンドの変更は禁止です

レギュレーション

プログラムがやっていること

エントリーポイントとなる index.php を見てみましょう。

コアとなるロジックは、

  • クエリストリングのキーと値の組み合わせを tokens テーブルに保存。
  • 値降順(第一ソート順), キー降順(第二ソート順)でとりだし、3番目の値の文字列を取得し逆さにする
  • HTMLテンプレートに文字列を埋め込んで表示

という感じでした。

vendors ディレクトリ、データベースアクセスを取り除く

初期のスコアは400万を超えていますが、その大部分が vendors ディレクトリであることがわかります。 プログラムを把握した上であらためてレギュレーションを確認してみると、データベースに関してはなんら記述がないので、データベースへ保存するコードを除去できます。 よって、受け取ったクエリストリング配列を処理して、レンダリングに必要な文字列を返すコードと、その他のHTMLを全てindex.php に入れれば、大分スコアが減らせそうです。そうして出来たコードにインデント・スペースを補完したコードが以下。

<?
    $a=$_GET;
    krsort($a);
    arsort($a);
    echo strrev(array_values($a)[2])
?>

最初のforeach で配列を整形してる部分をなくせないかな、と思いましたが思いつかなかったです。 ユーザー定義のソート関数ではキーと値のソートルールが同じだったので、$i = $a[1] != $b[1];$itrueなら値、false ならキーでソートされます。

コードゴルフなのに、そこそこ読みやすいコードになってしまいましたね。

short open tag

short open tagは将来的に廃止されそう(PHP: rfc:deprecate_php_short_tags)ですが、PHP 7.3.2ではまだ動作しますし、マネクラの環境でもデフォルトで使えます。タグとforeach キーワードの間にスペースが無くても動きます。

不要なファイルを削除する

これで、 vendors も削除できますし、 model/token.php も不要になりました。表示に必要なファイルは、 index.php, mc.png の2つになったので、改変不可な make check ファイルを含む Makefile を入れて、3ファイル以外の全てのファイルを削除しましょう。 .env, .htaccess が無くてもDiffチェッカーはパスします。

HTMLドキュメントを短くする

残るはHTMLを短くするのみです。PNGファイルは、名前を変える以外の変更はしていません。

無駄なCSSを取り除く。

lolipop-mc-codegolf-challenge/home.liquid at master · pepabo/lolipop-mc-codegolf-challenge · GitHub

CSS定義でファイルサイズがかなり大きくなってます。 まず、HTMLにはクラス属性が1個も定義されてなかったので、セレクタにクラスを含むものは安全に削除できます。 使ってないタグを含むセレクタの定義も削れます。 結果以下が残りました。

body {
    height: 100vh;
    font-family: Helvetica;
    letter-spacing: .04em
}
table {
    height: 100%
}
* {
    border: none;
    padding: 0;
    margin: 0;
    font-weight: 400;
    color: #465560;
    text-align: center
}
td {
    height: 50%;
    width: 5%
}

font-family は、レンダリングに使われている物だけをのこしました。画面に表示されている文字列要素が h2 だけだったので、 * に統合することができました。

表示に影響しないタグを削除していく

<html><header><meta><body> などを削ってもチェッカーにパスしました。

表示に影響しない閉じタグを削除していく

一箇所 </table> が残りましたが、それ以外は削除できます。 </style> については、ドキュメントの最後に移動すると、削除できます。 ところどころにある &nbsp; も不要です。

属性値を"で囲まない

はい。業務で真似してはいけない。

DOCTYPE宣言

<!DOCTYPEhtml>

宣言内のスペース不要でした。

pngファイル名をmc.pngm

5文字縮まりましたね。拡張子なんていらなかった。

まとめ

これで解説は終わりです。 全般的に業務で役に立たない知識です。

没テクニック

テーブルレイアウトをやめてdivにする

挑戦しましたが、Diffが出てしまうので断念。

PNGファイルサイズを縮める

PNGファイルからアルファチャンネルを削除すれば、スコアを縮められるかと思ってGIMPでやってみましたが、Diffチェッカーに引っかかって失敗しました。サイズは8,000ほど縮まりそうだったので残念です。

レギュレーションを守った上で最高のスコアは

なんと0になります。スコアチェッカーのコマンドは以下の通りですが、 *.git/*, Makefile, .env が除外されているため、.git/ ディレクトリ以下に index.php, mc.png を移動して、シンボリックリンクを作れば、レギュレーションを完全に守った上で0が達成できます。 チェッカーで除外するのではなく、デプロイ時に除外すればこの穴はできないので、運営側で意図した穴なのかな、と思います。

@ssh -p ${SSH_PORT} ${SSH_USER}@${SSH_HOST} 'find /var/www/html -type f -not -iwholename "*/.git/*" -not -name "Makefile" -not -name ".env" | xargs cat | wc -c'

55型有機EL TVとサウンドバーの感想

55型有機EL TV (OLED55C8PJA)

ヨドバシ.com - LGエレクトロニクス OLED55C8PJA [有機ELテレビ 55V型 4K対応 OLED55C8P]

1年前発売・有機EL 55型で一番安いLG製を購入。10年前に買ったSHARP製32型液晶からの買い換え。 NetflixとAmazon Prime, Youtube, Nintendo Switch用に。

良かったと思うところ

  • 黒が黒い
  • いままでPC接続でEIZO FlexScan 27.0インチ ディスプレイモニター (4K UHD/IPSパネル/ノングレア/ブラック/USB Type-C搭載/5年間保証&無輝点保証) EV2785-BKでNetflixを見てたけど、Safariで見ないと高画質にならないらしく不便でした。あとPCを操作しないといけないので、早く見たいとかながら見とかしにくい。そのあたりの障害が取り除かれました
  • Nintendo Switchをスリープ解除したらTVも起動してHDMIに自動切り替えしてくれるので楽
  • リモコンが変な形だけど、直立できるのは便利かもしれない
  • サウンドバーとHDMI 接続してる。両方がHDMI-ARCという仕様に対応してて、別途線を付けなくてもいいし、TVのリモコンでサウンドバーの音量を操作できる

いままであった32型液晶は過去7年くらい、地上波を見なくなって、ほぼ使ってなかったけど、これはNetflix, Amazon Prime, YouTube用に長く使えそうな気がします。 4Kはコンテンツがまだ少ないと感じる。Amazon Primeの4Kコンテンツは綺麗ですが、まだまだ数が少ない。

微妙なところ

  • 電気代。55型だし仕方ない…
  • フレーム補完機能。既定でオンですが、オフにしてます

サウンドバー

ヨドバシ.com - ヤマハ YAMAHA YAS-408(B) [MusicCast BAR 400 フロントサラウンドシステム]

薄型テレビはスピーカーが弱いらしい、ということで。あとSpotify ConnectとBlueToothスピーカー機能目当て。 いままで使っているスピーカーはGX-D90(Y) (色違いのGX-D90(B)はまだ新品を売ってる)を、大学のときから15年くらいPCスピーカーとして使っていて、壊れるまでこれでいいや、と思ってますが、TV用に別途欲しくなり。

良かったところ

  • TVの電源に連動して自動ON/スリープしてくれる
  • Spotify Connect は期待通り。PCでもスマホでも操作できて、スピーカーは同一のものが使える
  • iPhone/MacのiTunes/ミュージックアプリからの再生でも自動電源ON/スリープしてくれる
  • サブウーファー(いままで使ったことない)、いままで聞いてた曲を再生しても、聞こえなかった低音が出るので良かった。

微妙なところ

  • どうしようもないことかもしれないけど、Bluetooth 経由の再生開始に1秒強の時間がかかるのが気になる

ドラム式洗濯機 Cuble (NA-VG2300L-X) 感想

ヨドバシ.com - パナソニック PANASONIC NA-VG2300L-X [ななめドラム式洗濯機 Cuble(キューブル) 洗濯・脱水10kg/乾燥5kg 左開き プレミアムステンレス]

同僚に「ドラム式は人権だ」、と言われたので、高いものを買いました! ヨドバシカメラ秋葉原で28万円、ポイント差し引いて5年保証を付けて実質24万ちょいで購入。 洗濯物を入れてボタン2つ(電源、スタート)を押すと3時間後に乾燥して出てくる魔法の箱を手に入れた、という感じです。 10年ほど、ずっと部屋干ししていたので、以下の手間が無くなりました。

  • 洗剤を洗濯前に入れる手間
  • 洗濯後に干す手間
  • 乾燥後に洗濯物を取り込む手間

いままで使っていた縦型の洗濯機(8年前購入)にも乾燥機能は付いていましたが、シワだらけになったので、2, 3回使ってやめました。 ドラム式だからかシワも気にならなくて、毎回乾燥させてます。

電気代が増えたかどうかについては、まだよく分からないです。 同時期にテレビも買ったので、そちらでは増えてる気がします。

12年ぶりにまとめて家電を買った

いま使っているものがだいたい8〜12年使っているものばかりで、オーブンレンジと冷蔵庫は使えなくもなっている。 便利なものが出てきているらしいのでまとめて買い換えることにしました。勢いが大事…

すべてヨドバシカメラアキバかヨドバシ.comで買ったのでヨドバシのリンクも付けます。

商品を使ったら感想も書きたい。

ドラム式洗濯機

同僚にドラム式を強くお勧めされました。 洗濯物を干す必要がなくなると、自由な時間が増えるということらしいので、高価なものを買いました。

ヨドバシ.com - パナソニック PANASONIC NA-VG2300L-X [ななめドラム式洗濯機 Cuble(キューブル) 洗濯・脱水10kg/乾燥5kg 左開き プレミアムステンレス]

ドラム式洗濯機 Cuble (NA-VG2300L-X) 感想書きました。

冷蔵庫

12年前にリサイクルショップで購入したものが最近壊れたので。 上にオーブンレンジを載せられて、自動製氷機能がついてるものがAQUAしかなかったです。

ヨドバシ.com - AQUA アクア AQR-SV24H(K) [冷蔵庫(238L・右開き)ヴィンテージブラック]

買ってから3週間後

まだ飲み物くらいしか入れてない。自動製氷は便利。

オーブンレンジ

同じく12年前にリサイクルショップで購入したものが最近壊れたので。

ヨドバシ.com - シャープ SHARP AX-CA450-W [ウォーターオーブン ヘルシオ 18L 1段調理 ホワイト系]

まだレンジ機能しか使ってない

テレビ

Netflix とNintendo Switch用で、地上波はあまり見ないと思います。

ヨドバシ.com - LGエレクトロニクス OLED55C8PJA [有機ELテレビ 55V型 4K対応 OLED55C8P]

サウンドバー

ヨドバシ.com - ヤマハ YAMAHA YAS-408(B) [MusicCast BAR 400 フロントサラウンドシステム]

コードレス掃除機

ダイソン 掃除機 コードレス Dyson Cyclone V10 Fluffy SV12FF SV12 FF

ダイソン 掃除機 コードレス Dyson Cyclone V10 Fluffy SV12FF SV12 FF

ヨドバシ.com - ダイソン Dyson SV12FF [Dyson V10 Fluffy コードレススティッククリーナー ニッケル/アイアン/コッパー]

コードレスは便利。重いけどハンドクリーナーにもなる。集塵部分が丸見えなので、定期的に捨てられる。 付属のアタッチメントを付け替えるとベッドの掃除もできる。有名な白い粉(ハウスダスト)が取れるので週1で掃除するようになる。

PHPerKaigi 2019にて「PhpStormでコードを理解する技術」というテーマで発表しました

2019年3月29〜31日にかけて開催されたPHPerKaigi 2019の2日目に発表してきました。

KeynoteファイルもDropboxで公開します。 こちらは、そのうち削除するかもしれません。

この発表はイベントの少し前に公開した以下の4記事+補足記事で説明した話を15分のダイジェスト版という位置づけで発表しました。

PHPプロジェクト向けの定番IDEであるPhpStormに使い慣れていくと、「コードを理解する」というシンプルな目的のためでも多くの機能を使ってると思ったので、それをまとめるだけでもコンテンツになりそうだな、と思って応募しました。

発表にあたりいろいろな先人の記事を参考にし、Twitterで知らなかったテクニックを教えて頂きました。特に5名の方にあらためて感謝いたします。

PHPerKaigi 2019に参加して

参加者同士の交流を促進するための仕掛けがよく練られていてすごいと思いました。特によいと思ったのが

  • PHPerチャレンジ
  • (去年に引き続き)Interactive Round Table
  • お茶会(懇親会)でのボードゲーム

です。ボードゲーム以外参加できませんでしたが…。

2週間くらいまえからブログ記事で作っていったのですが、肝心のスライドが前日まで完成せず、1日目はずっともくもくコーナーで資料作成していたため、セッションの聴講や参加者とのコミュニケーションができず辛かったです、次は事前に準備をして望みたいです。

PhpStorm でコードを理解する (テストコードを読む・実行する・書く編)

(※諸事情によりテスト実行の準備を省略している、後で加筆したい。)

テストコードを読む

もし、前述のフィボナッチ数列を出力するコードにテストコードがあれば、コードを実行しなくても理解できた可能性が高い。テストコードは、欠陥の検出につかうツールでもあり、コードの振る舞いについて表現したドキュメントにもなるからだ。

フィボナッチ数列を出力するコード(再掲)

<?php
// nazono.php
function nazono() {
    $a = 0;
    $b = 1;
    for ($i = 1; $i <= 10; $i++) {
        $l = $a;
        $a = $b;
        $b += $l;
        print "$a\n";
    }
}
nazono();

nazono() 関数がどのように使われているか調べようとして、定義箇所で、Command+B (Mac), Ctrl+B (Win)を押したときに、テストコードが引っかかったらラッキーかもしれない。移動してみよう。

f:id:tenkoma:20190324201231p:plain
nazono() 関数がテストコードから呼び出されていたら…

ちなみにテストコード例。

<?php
namespace Nazono\Tests\Unit;

require_once __DIR__ . '/../../nazono.php';

class NazonoTest extends \PHPUnit\Framework\TestCase
{
    public function testNazono()
    {
        // 実コードを呼び出す
        nazono();
        // 想定した出力
        $expectOutput = <<<OUT
1
1
2
3
5
8
13
21
34
55

OUT;
        $this->expectOutputString($expectOutput);
    }
}

期待される出力がテストコードに書かれている。 コードを実行した結果をみるのと同じ効果が得られるのがわかると思う。

テストを実行する・書く(変更する)

  • Mac: Shift+Ctrl+R, Win/Linux: Shift+Ctrl+F10

上記のテストを実行してみる、成功したら、「生きた」テストであることがわかる。

f:id:tenkoma:20190324205815p:plain
PhpStorm から NazonoTest テストを実行した

失敗したら、実コードかテストコードのどちらかが間違っている可能性がある。*1

もしプログラムの正しい振る舞いが分かっていれば、テストコードか実コードを変更することで、実コードへの理解が深まるかもしれない。 テストを書くのが楽になる機能に「Auto-test」がある。有効にすると、ファイル変更を検知して、自動で再テストしてくれる。

f:id:tenkoma:20190327001651p:plain
Auto-test ボタン

もし複雑なコードを良く理解しないといけない場合、テストがコードを理解するためのツールになると思う。

目次

*1:それ以外の、テストのセットアップができていない可能性もある