$shibayu36->blog;

$shibayu36->blog;

クラスター株式会社のソフトウェアエンジニアです。エンジニアリングや読書などについて書いています。

OSS向けに英語を書くためにChatGPTのProjectsを活用している

GitHub上のOSSにcontributeするためにcommitメッセージやPullRequestのコメントを英語で書くことがある。もう自分で英語を書くのは無理なので自動翻訳を活用したい。この時DeepLなどを使ってもいいのだが、もう少しチューニングを加えたい。たとえば

  • 英語非母語話者同士の会話になることが多いので、できるかぎり平易な表現を使う
  • 1行の場合はcommitメッセージとして、複数行の場合はPullRequestのコメントとして翻訳したい
  • すぐに使えるようにgit commit用のコマンドやMarkdownで出力したい

などなど。

そこで最近はChatGPTのProjectsを使って翻訳をしている。

たとえばこんな感じに指示を用意しておいて

ソフトウェアエンジニアリングでのコミュニケーションに用いるために和英翻訳をします。以下のことに注意して翻訳してください。

- 英語非母語話者でもすぐに分かるように、平易な英語に翻訳してください
- GitHubのissueや、gitのcommit messageに使いやすい翻訳にしてください

## 出力のルール
- 翻訳文のみの出力で良いです
- ダブルクオートは"、シングルクオートは'を使ってください。もしコマンドライン形式の場合、適切にエスケープして誤ってクオートが閉じられないようにして
- 1行の日本語の場合はcommit message用と考え、`git commit -m "(翻訳文)"` というコマンドライン形式で出力してください。ピリオドは不要です
- 複数行の日本語の場合はGitHubへのコメント用と考え、コピーしやすいようにMarkdownでpreに囲んで出力してください

こういう風に質問するとcommitメッセージ用のコマンドが出力される。

さらにこういう風に質問するとPullRequestのコメント用のMarkdownが出力される。

これであとはコピペするだけで良い。便利。

本当は以下のような工夫をもうちょいしたいが、まだそこまでは出来ていない。

  • そもそもChatGPT UIを使うのではなく、もっと素早く利用したい
    • 例えばRaycastのようなショートカットで使える、git commitのフックを使うと自動翻訳してcommitするなど
    • ただChatGPTに課金してるのにAPI Tokenを使う形式でお金がかかるともったいないなと感じてるので、やり方検討中

リアルタイムに2次元位置を同期するサーバーで爆弾を置けるようにした

clusterのリアルタイム通信サーバーの漸進的な進化のような仕組みを理解したいなと思い、手習い用にMQTT+Protocol Buffersを使ってリアルタイムに2次元位置を同期するサーバーを書いてみている。今回はリアルタイムに2次元位置を同期するサーバーでプレイヤーから弾を発射できるようにの続きで、プレイヤーが爆弾を配置できるようにした。

できたもの

client側でBボタンを押すとその場に爆弾を配置できる。爆弾はしばらくすると爆破し、火に当たるとプレイヤーはやられる。

実装コードはこの辺り

処理の流れ

このような形になった。

  • 爆弾と爆弾の火はアイテムのタイプとして分離する
  • Game structにすべて任せるとどんどん肥大化してしまうため、それぞれの状態管理はそのアイテムごとに任せるようにした。衝突した時に何をするかなどもアイテムに任せる
  • アイテム生成や自身の削除を行いやすくするため、Gameに対して一部のオペレーションを依頼することを可能にする

アイテム自身にTickの更新が起きた時や衝突が起きた時のロジックを任せる

アイテム自身にTickの更新が起きた時や衝突が起きた時のロジックを任せるという部分だけ工夫したので書いておく。

Game structがどんどん肥大化しそうな気配があったので、アイテム自身にロジックを任せることにした。Tickの更新が起きるたびにアイテムのUpdateが呼ばれ、他のアイテムとの衝突が起きるたびにOnCollideWithが呼ばれるようにする。

まとめ

今回はリアルタイムに2次元位置を同期するサーバーで爆弾を置けるようにした。爆弾を置こうとすると、ロジックをどこに置いたら分かりやすくなるかを考える必要が出てきて勉強になった。

Google Spreadsheetで他のマスターデータを読み込んでいるとき列追加で壊れにくくしたい

Google Spreadsheetを使っているとき、別のマスターデータシートから特定列だけ読み込みたい時がある。この時簡単に読み込む方法としてはIMPORTRANGEやQUERY関数を組み合わせて使う方法がある。

ただこのやり方だと、マスターデータシートに列が追加された時に壊れやすいという問題がある。QUERY関数などはヘッダー名を指定して読み込むことができず、SELECT Col1, Col3 のような書き方をする必要がある。これだとマスターデータの途中に列を追加した場合に簡単に壊れてしまう。

そこでマスターデータシートのヘッダー名をキーにして読み込む方法を考えてみた。サンプルは こちらのspreadsheetにおいている。

できること

以下のようなマスターデータがあるとして

別シートで一部だけ読み込みたい。この時にマスターデータに列追加しても壊れないようにしたい。

ヘッダー名をキーにして読み込む方法

やり方としては読み込みたい列ごとに次のような関数を書くこと。これだけで、masterというシートから「名前」というヘッダーの列をすべて読み込める。

=INDEX(master!A1:Y, 0, MATCH("名前", master!1:1, 0))

もう少し関数の意味をコメントで解説する。

// MATCHでとってきた列番号を元に、その列を全てIMPORTする
=INDEX(
  master!A1:Y,
  // INDEXの第二引数に0を指定すると全行を返す(列全体を対象)
  0, 

  // どの列番号を読み込むかをMATCHを使って決める
  // ヘッダー行から「名前」に完全一致する列番号を取得できる
  MATCH(
    "名前",
    master!1:1,
    0 // 完全一致モード
  )
)

このやり方を使えばマスターデータシートの変更に多少強くデータを読み込めて便利である。

別のspreadsheetからも読み込みたい場合

また別シートではなく別のspreadsheetから読み込みたい時はIMPORTRANGEと組み合わせれば良い。こんな感じ。

=INDEX(IMPORTRANGE("<sheet URL>", "master!A1:Y"), 0, MATCH("ColName", IMPORTRANGE("<sheet URL>", "master!1:1"), 0))