タイトル: 型の確認
SEOタイトル: 各言語での型確認方法完全ガイド — Python/JS/Java/PHP
| この記事の要点 |
|
型を確認する場面
動的型付け言語 (Python / JavaScript / PHP / Ruby) では、変数の型が実行時に決まるため、関数の引数チェックやデバッグで「いま何の型が入っているか」を調べたい場面が頻発します。本記事では各言語での型確認方法をまとめます。
Python
x = 42
y = "hello"
z = [1, 2, 3]
# type() で型オブジェクトを取得
print(type(x)) # <class 'int'>
print(type(y)) # <class 'str'>
print(type(z)) # <class 'list'>
# 名前だけ取り出す
print(type(x).__name__) # 'int'
print(x.__class__.__name__) # 'int' (同等)
# 厳密一致 (継承を見ない)
if type(x) is int:
print("int です")
# isinstance: 継承を考慮 (推奨)
print(isinstance(x, int)) # True
print(isinstance(True, int)) # True (bool は int のサブクラス)
print(isinstance(x, (int, float))) # 複数型 OK
# クラスでの利用
class Animal: pass
class Dog(Animal): pass
d = Dog()
isinstance(d, Animal) # True (継承を見る)
type(d) is Animal # False (厳密一致)
# Python 3.10+ の Pattern Matching
match z:
case list() if all(isinstance(i, int) for i in z):
print("整数のリスト")
case dict():
print("辞書")
case _:
print("その他")
typing による型ヒント (Python 3.5+)
from typing import List, Dict, Optional, Union
def greet(name: str, count: int = 1) -> str:
return f"Hello, {name}!" * count
def process(items: List[Dict[str, int]]) -> Optional[int]:
return sum(d.get("score", 0) for d in items) or None
# Python 3.10+ では Union を | で書ける
def parse(value: int | str | None) -> str:
return str(value)
# 静的解析: mypy / pyright で検証
# $ mypy myscript.py
JavaScript
// typeof でプリミティブ判定 (7 種類の文字列を返す)
typeof 42; // "number"
typeof "hi"; // "string"
typeof true; // "boolean"
typeof undefined; // "undefined"
typeof Symbol(); // "symbol"
typeof 10n; // "bigint"
typeof function(){}; // "function"
typeof {}; // "object"
typeof null; // "object" ← 歴史的バグ
typeof []; // "object" ← 配列も object
// 配列判定は Array.isArray() を使う
Array.isArray([]); // true
Array.isArray({}); // false
// null 判定
const v = null;
v === null; // true (推奨)
typeof v === "object" && v === null; // 冗長
// instanceof: コンストラクタチェック
[] instanceof Array; // true
new Date() instanceof Date; // true
// Object.prototype.toString.call() で精密な型名
Object.prototype.toString.call([]); // "[object Array]"
Object.prototype.toString.call(null); // "[object Null]"
Object.prototype.toString.call(new Date()); // "[object Date]"
// ユーティリティ関数
function getType(x) {
return Object.prototype.toString.call(x).slice(8, -1).toLowerCase();
}
getType([]); // "array"
getType(null); // "null"
getType(new Map()); // "map"
TypeScript
// 静的型でコンパイル時に検証
function add(a: number, b: number): number {
return a + b;
}
// Type Guard で実行時の絞り込み
function process(value: string | number): string {
if (typeof value === "string") {
return value.toUpperCase(); // ここでは string と確定
}
return value.toFixed(2); // ここでは number と確定
}
// ユーザ定義 Type Guard
function isUser(obj: unknown): obj is { name: string; age: number } {
return typeof obj === "object" && obj !== null
&& "name" in obj && typeof (obj as any).name === "string"
&& "age" in obj && typeof (obj as any).age === "number";
}
Java
Object x = "Hello";
// getClass: ランタイムの実クラスを取得
Class<?> c = x.getClass();
System.out.println(c.getName()); // java.lang.String
System.out.println(c.getSimpleName()); // String
// instanceof: 型チェック (継承も見る)
if (x instanceof String) {
String s = (String) x;
System.out.println(s.length());
}
// Java 16+ Pattern Matching for instanceof
if (x instanceof String s) {
System.out.println(s.length()); // キャスト不要
}
// Java 21 Switch Pattern Matching
String describe(Object obj) {
return switch (obj) {
case Integer i -> "整数: " + i;
case String s when s.isEmpty() -> "空文字列";
case String s -> "文字列(" + s.length() + ")";
case int[] arr -> "int 配列(" + arr.length + ")";
case null -> "null";
default -> "その他: " + obj.getClass().getSimpleName();
};
}
// Class.isInstance() (動的判定)
Class<?> klass = String.class;
boolean ok = klass.isInstance(x);
PHP
$x = 42;
$y = "hello";
$z = [1, 2, 3];
// gettype: 文字列で型名取得
gettype($x); // "integer"
gettype($y); // "string"
gettype($z); // "array"
gettype(null); // "NULL"
// is_*() 系 (推奨)
is_int($x); // true (is_integer も同じ)
is_string($y); // true
is_array($z); // true
is_bool($v);
is_float($v); // is_double, is_real も同じ
is_null($v);
is_numeric("123"); // true (文字列でも数値ならtrue)
is_object($obj);
is_callable($fn);
// クラス確認
class User {}
$u = new User();
get_class($u); // "User"
$u::class; // "User" (PHP 8.0+)
get_parent_class($u); // 親クラス名 or false
// instanceof
$u instanceof User; // true
// 名前空間付き
use App\Models\User;
$u instanceof \App\Models\User; // true
// PHP 8 の型宣言
function greet(string $name, int $count = 1): string {
return str_repeat("Hello, $name! ", $count);
}
// Union 型 (PHP 8.0+)
function parseValue(int|string|null $v): string {
return (string) $v;
}
// readonly プロパティ (PHP 8.1+)
class Point {
public function __construct(
public readonly float $x,
public readonly float $y,
) {}
}
主要言語の対応表
| 機能 | Python | JavaScript | Java | PHP |
|---|---|---|---|---|
| 型名取得 | type(x).__name__ | typeof x | x.getClass().getSimpleName() | gettype($x) |
| 厳密一致 | type(x) is int | typeof x === "number" | x.getClass() == Integer.class | is_int($x) |
| 継承考慮 | isinstance(x, int) | x instanceof Number | x instanceof Integer | $x instanceof Foo |
| 配列判定 | isinstance(x, list) | Array.isArray(x) | x.getClass().isArray() | is_array($x) |
| null 判定 | x is None | x === null | x == null | is_null($x) |
デバッガでの型確認
- VS Code (Python / Node.js / PHP): ブレークポイントで止めて Variables パネルに型と値が表示
- IntelliJ / PyCharm: 同様、Watches で
type(x)を評価可能 - Chrome DevTools: console の
console.dir(x)で詳細プロパティを表示 - Xdebug (PHP):
var_dump($x)でステップ実行中の値・型確認 - jdb / IntelliJ Debugger (Java): 変数の宣言型と実行時型を別表示
静的解析で実行時チェックを減らす
| 言語 | 静的解析ツール |
|---|---|
| Python | mypy / pyright / Pyre |
| JavaScript | TypeScript / JSDoc + tsc --checkJs |
| PHP | PHPStan / Psalm |
| Ruby | RBS + Steep / Sorbet |
これらを CI に組み込むと、実行時の isinstance / typeof チェックは大幅に減らせます。
FAQ
Q: Python で type と isinstance どちらを使うべき?
A: 原則 isinstance。継承を尊重するため。例外的に「特定クラスの厳密一致」が必要なときだけ type(x) is Foo。
Q: JavaScript で typeof null === "object" はなぜ?
A: 初期実装の歴史的バグです。後方互換のため修正されないままです。null 判定はx === nullと書きましょう。
Q: PHP で is_int("123") が false なのは?
A: 厳密に「整数型」かを見るからです。「整数として解釈可能」を確認したいなら is_numeric() や ctype_digit() を使います。