土日に島根のほうまで1泊でドライブに行っていた。
松江フォーゲルパーク に行った。
出雲大社にも行った。あんまり時間がなくて、参道をふらっとまわってお参りしたぐらい。
宿泊は奥出雲多根自然博物館に泊まった。ぱらのまの聖地巡礼。
土日に島根のほうまで1泊でドライブに行っていた。
松江フォーゲルパーク に行った。
出雲大社にも行った。あんまり時間がなくて、参道をふらっとまわってお参りしたぐらい。
宿泊は奥出雲多根自然博物館に泊まった。ぱらのまの聖地巡礼。
Steep で不要な RBS::Location#to_s
の呼び出しを消すPRを作った。
RBSのメモリ使用量を減らす前準備。
RBSのメモリ使用量を減らすために色々やっているのだけど、計測用にベンチマークスクリプトを毎回書いているのは面倒なので、rbsのリポジトリに追加するPR。
Cを書いていて、謎のセグフォが出てそこそこ悩んだ。雰囲気は次のようなコード
#include <stdio.h> #include <stdlib.h> typedef struct { int id; int value; } entry; typedef struct { int len; int cap; entry entries[0]; } table; table *table_new(int cap) { table *t = malloc(sizeof(table) + sizeof(entry) * cap); t->len = 0; t->cap = cap; return t; } int main(void) { table *t1 = table_new(1000); for (int i = 0; i < t1->cap; i++) { t1->entries[i].id = i; t1->entries[i].value = i * 10; t1->len++; } table t2 = *t1; printf("t1 last value: %d\n", t1->entries[t1->len-1].value); printf("t2 last value: %d\n", t2.entries[t2.len-1].value); return 0; }
t1
もt2も同じstructなので同じ値が出力されると思いきや、私の手元だと
t2`を出力するところでセグフォが出てしまう。
t1 last value: 9990 zsh: segmentation fault ./a.out
この問題に最初遭遇したときは、t2
の方の書き方だけをしていたので、セグフォの原因がさっぱりだった。
その後t1
の書き方をすると解決することに気がついたのだけど、「えっ->
と(*v).
ってsyntax sugerの関係なんじゃないの??」としばらく理解ができていなかった。
これの答えが何だったかと言うと、構造体をコピーしていることが原因だった。
まず、entry entries[0]
の部分が影響している。これは可変長構造体、みたいな用語(正確な用語は知らない)のテクで、メモリ使用量を抑えるのに便利。
https://satosystems.hatenablog.com/entry/20100916/1284637817 とかを参考にしていた。
これは構造体の直後のメモリ領域に配列のためのメモリ領域を確保して、構造体に配列へのポインタをもたせることなく可変長の配列を実現している。便利。
ところが、table t2 = *t1;
で t1
を別のローカル変数であるt2
にコピーしている。ということは、このt2
が保存されているアドレスはもともとmalloc
してきたアドレスとは異なるということ。t2.entries
はt2
の直後の領域を参照しようとして、セグフォになってしまっていた。
rspec-request_describer に PR をしていた。
RSpec で context
を差し込むところを間違えたら、rspec-request_describer 内部でエラーが起きていてエラーの意図を掴むのにちょっと手間取ったので、エラーをハンドルしてどういうエラーなのか分かりやすいようにしてみた。巨大describe
になってくるとインデントが迷子になりがち。
速攻マージ&リリースされたので、迷子になりがちな人はアップデートすると良さそう。
最近(といっても数ヶ月前からだけど)は、ピアノで海の見える街を練習している。ピアノのやる気に満ち溢れている期がやってきたので、割と進捗が良い。
曲のイメージをもうちょっと膨らませたくなって、魔女の宅急便の映画を見たりもした。配信がなくて、仕方なくDVDを買った。
昨日1年ぶりにTOEICを受けていた。点数が少し落ちたけれどそこまで大きな差はないので、この得点はまぐれではなかったのだなという気持ちになった pic.twitter.com/eO4zhO0hpl
— 🎹 (@p_ck_) March 26, 2024
TOEIC IPテストを受けた。860点。
前回から20点下がったが、ツイートにもある通り大きな差ではないので、前回がまぐれでなかった安堵のほうが大きい。
とはいえもうちょっと勉強していきたいなの気持ちでabceedを再開した。
前回受けたのは半年ぐらい前だったかなーと思っていたので、1年も経っていたのはちょっとびっくりした。
ちなみに点数の推移は、680点(2022-04-12), 795点(2022-12-01), 880点(2023-03-01), 860点(2024-03-26)となっている。次は900超えたいなー
「追放されたチート付与魔術師は気ままなセカンドライフを謳歌する。 ~俺は武器だけじゃなく、あらゆるものに『強化ポイント』を付与できるし、俺の意思でいつでも効果を解除できるけど、残った人たち大丈夫?~」を最近読んだ。
「あーはいはいよくある追放ものね」と思っていたら、完全に異常で良かった。なろう系だと思わず異常漫画だと思って読んでみるのをめっちゃおすすめ。
activerecord-originator の型定義周りを軽く修正していた。
型の変更しか入っていないけれど、v0.2.1をリリースした。
graphql-coverage でも同様の型の修正をしていた。
graphql-coverage を久々にいじっていたら、新しいRubyのバージョンでCIが走っていなかったので有効にした。
activerecord-originator、ここ数日毎日数件海外の人っぽいstarが増えているのだけど、どこからこれが見つけられているのかがさっぱりわからない。 もっと海外にリーチしていきたいのでヒントがほしい…
activerecord-originator
にベンチマークスクリプトを追加した。
これを追加したことによって、どの程度パフォーマンスが劣化しているかが分かった。単純に#to_sql
を呼び出す場合で3倍ぐらい、実際にselectクエリを発行する場合でも2倍ぐらいの速度差が出ていた。クエリを発行しているのはメモリ上のsqliteだし、レコードも100件しか作っていないからあまり現実的な比較ではない。
activerecord-originator
の速度改善をした。今まではすべてのNodeを拡張してinitialize
時にcaller
を保存していたのだけど、これをクエリに位置情報を差し込みたいNodeだけ拡張するようにした。
これによって、#to_sql
は71~78%程度、クエリの実行は84~86%程度の速度劣化に抑えられた。
これだけ速度劣化が小さく出ていれば、実アプリケーションに入れたときの速度差は気にならないぐらいになっていそう(たぶん)。単純なクエリ実行の例だと、1回あたり0.02ミリ秒しかオーバーヘッドが乗ってない計算になりそう。
この変更を入れたのでv0.2.0をリリースした
そういえばIS NULL
とかを考えていなかったな、と思ってテストを書いてみたら、特に何もせず通って便利だった。
すでに実装は済んでいたけど、テストがあったほうが後々嬉しくなる可能性がありそうなのでテストだけ追加した。
where("title LIKE ?", "%#{title}%")
みたいなやつの対応を考えていたのだけど、むずそう。
これはSqlLiteral
nodeとして扱われるのだけど、このNodeが特殊で、どうやら作られるタイミングは#where
が呼ばれるタイミングではなく#to_sql
が呼ばれるタイミングっぽい。それだとこのnodeのinitializeにhookしてもほしい位置情報が取れなくて困る。
いい解決方法あるかなあ。あんまり思いつかない。where
メソッドを上書きして…とかやればできるだろうけどやりたくないよねえ