こんにちは!Hack言語の世界へようこそ。チーフアーキテクトの私です。
他のプログラミング言語、例えばPHPやJavaScriptなどからHackの世界に飛び込んできたとき、多くの開発者が最初に感動し、そして少しだけ戸惑うのが「厳格な静的型システム(Strict Mode)」です。型チェッカーが私たちのコードを隅々まで見張り、実行時エラーの芽を片っ端から摘み取ってくれるあの感覚は、慣れると本当に手放せなくなりますよね。
さて、今回はそんなHackの型システムの中でも、データの「集まり」を扱うときに必ず直面する「Tuple(タプル)」型と「List(ベクター/コレクション)」型の使い分けについて、徹底的に深掘りしていきましょう。
「要素数が決まっているデータ」と「可変長のデータ」、それぞれにどの型構造を選ぶのがベストなのか?ここをクリアすれば、あなたのHackコードは一気に洗練され、型安全の要塞と化しますよ。それでは、一緒に見ていきましょう!
—
1. Tuple型とList型って、そもそも何が違うの?
まずは、頭の中でイメージしやすいように、この2つの違いを整理しておきましょう。
- Tuple(タプル)型:【固定長・異種混合】
- イメージ:「ロッカーの番号が決まっていて、中身の指定席がある状態」
- 特徴:要素数がガチガチに固定されており、何番目に何型が入るかが厳密に決まっています。中身のデータ型がバラバラでもOKです。
- List(リスト / ベクター)型:【可変長・同種混合】
- イメージ:「買い物のメモ用紙。上から順に同じ種類のアイテムをいくらでも書き足せる状態」
- 特徴:要素数が伸縮します(増えたり減ったりする)。ただし、基本的には「すべて同じ型(同種)」のデータを扱います。
【Tupleのイメージ】 (固定長・型バラバラ)
[ 0番目: string ] [ 1番目: int ] [ 2番目: bool ]
“User-001” 42 true
【Listのイメージ】 (可変長・型統一)
[ int ] -> [ int ] -> [ int ] -> …
10 20 30
この違い、なんとなく掴めましたよね?それでは、それぞれの具体的な使い方と、HHVMの裏側でどう扱われているのかを覗いてみましょう。
—
2. Tuple型:型安全な「構造体」のミニマム版
まずはTuple型です。HackにおけるTupleは `(T1, T2, …)` のように書きます。
例えば、「ユーザーのID(文字列)、年齢(整数)、アクティブ状態(真偽値)」をセットで関数から返したいとしましょう。わざわざ専用のクラスを定義するほどでもないな、という時にTupleは最高の相棒になります。
基本的なコードと意味
<<__Strict>>
namespace HackArchitect\Guide;
// ユーザー情報(ID, 年齢, アクティブフラグ)を返す関数
function get_user_profile(): (string, int, bool) {
// 順番と型が厳密に一致している必要があります
return tuple(“DEV-999”, 28, true);
}
function main(): void {
// タプルを受け取る
$profile = get_user_profile();
// 要素へのアクセス(0始まりのインデックス)
$userId = $profile[0]; // string型として推論される
$age = $profile[1]; // int型として推論される
// もしここで間違った型を期待すると、型チェッカーが即座に怒ってくれます!
// $invalid = $profile[0] + 1; // エラー: stringとintは足せません
echo “User: {$userId}, Age: {$age}\n”;
}
ここで陥りやすい罠:インデックスの魔力
初心者がやりがちなのが、Tupleの要素をマジックナンバー(`0`, `1`, `2`…)のままであちこちで使い回してしまうことです。「あれ?`[1]`って年齢だっけ、それともスコアだっけ?」となってコードが読めなくなります。
Tupleはあくまで「スコープが狭い関数間の受け渡し」や「一時的なペアリング」に留めるのが、美しいHackコードを書くコツですよ。要素が増えてきたら、迷わず `class` や `record` を定義しましょう。
—
3. List型(ベクター):伸び縮みするデータの安全な管理
次に、要素数が変わるデータの代表格である「List(ベクター)」を見ていきましょう。Hackでは通常、`vec
基本的なコードと意味
<<__Strict>>
namespace HackArchitect\Guide;
function process_scores(vec
$total = 0;
// 可変長のデータを安全にループ処理
foreach ($scores as $score) {
$total += $score;
}
return $total;
}
function main_list(): void {
// 整数のみを格納する可変長リスト
// 要素数は後から追加(Vec\pushなど)で増減可能
$myScores = vec[85, 90, 78, 92];
$sum = process_scores($myScores);
echo “Total Score: {$sum}\n”;
// 型違反の例:
// $myScores[] = “90”; // エラー!vec
}
HHVMの裏側:なぜ `vec` なのか?
少しだけアーキテクチャの話をしましょう。PHPの従来の `array` は、ハッシュマップ(連想配列)でありながらインデックス配列としても振る舞うという、メモリ効率の悪い「万能すぎる構造」でした。
しかし、Hackの `vec
—
4. どっちを選ぶべき?判断に迷ったときの指針
実際の開発現場で、「ここはTupleにすべきか?それとも `vec` にすべきか?」と迷ったら、以下の2つの質問を自分に投げかけてみてください。
1. 「要素の数は、実行中やビジネスロジックの中で増減しますか?」
- はい $\rightarrow$ 迷わず `vec
`(List) です。 - いいえ(決まった構造・ペア) $\rightarrow$ 次の質問へ。
2. 「要素の型はすべて同じですか、それとも位置によって異なりますか?」
- すべて同じ $\rightarrow$ 要素数が固定であっても、場合によっては `vec`(または固定長を保証したい場合は専用の構造)を検討しますが、単なるリストなら `vec`。
- 位置によって型が違う(例: 0番目は文字列、1番目は数値) $\rightarrow$ Tuple の独壇場です!
—
まとめ:型安全なデータ構造でHHVMを唸らせよう
今回は、Hack言語における固定長の「Tuple」と可変長の「List(`vec`)」の使い分けについて解説しました。
- Tuple `(T1, T2)`: 要素数固定・型混在OK。構造体の軽量版として、密なデータのやり取りに。
- List `vec
` : 要素数可変・型統一。HHVMの高速なメモリ管理の恩恵を受けながら、安全にコレクションを操作。
この2つを適切に使い分けられるようになると、あなたの書くHackコードの堅牢性は劇的に跳ね上がります。型チェッカーはあなたを縛る鎖ではなく、最高のエキサイティングな開発体験をもたらす相棒です。
ここをクリアできれば、Hackの基本はもうバッチリマスターできましたよ!自信を持って次のステップへ進んでくださいね。それでは、また次回のアーキテクチャ解説でお会いしましょう!