C#を用いたアプリケーション開発において、変数名やクラス名などの識別子を決定する際に必ず意識しなければならないのが「予約語」の存在です。
予約語はC#のコンパイラがプログラムの構造を解析するためにあらかじめ定義している特別な単語であり、開発者がこれらを自由に識別子として利用することは制限されています。
本記事では、C#における予約語の完全なリストから、特定の場面でのみ意味を持つコンテキストキーワード、さらには予約語を識別子として使うための特殊な記法まで、実務に直結する知識を詳細に解説します。
C#における予約語の定義と役割
C#の予約語とは、言語仕様によってその意味が固定されている単語のことであり、「予約済み識別子」とも呼ばれます。
これらの単語は、条件分岐を行うifや、クラスを定義するclass、データ型を指定するintなど、プログラムの論理構造を構築するために不可欠な要素です。
もし予約語をそのまま変数名やメソッド名として使用しようとすると、コンパイラはそれを「言語構造の一部」として解釈しようとするため、構文エラーが発生します。
例えば、int class = 10; というコードは、コンパイラが class をクラス定義の開始と認識してしまうため、ビルドに失敗します。
このように、予約語を正しく把握することは、無用なコンパイルエラーを回避し、スムーズなコーディングを実現するための基本となります。
予約語とコンテキストキーワードの違い
C#のキーワードには、大きく分けて「予約済みキーワード」と「コンテキストキーワード」の2種類が存在します。
- 予約済みキーワード (Reserved Keywords): プログラムのどの場所であっても識別子として使用できない単語です。
- コンテキストキーワード (Contextual Keywords): 特定のコードブロック内(特定の文脈内)でのみ特別な意味を持ち、それ以外の場所では識別子として使用できる単語です。
コンテキストキーワードは、C#がバージョンアップを重ねる中で、既存のプログラムとの互換性を保ちながら新しい機能を追加するために導入されました。
例えば、var や get は、特定の構文以外では変数名として利用することが可能です。
C#の予約済みキーワード一覧
C#で定義されている主要な予約済みキーワードを、その役割ごとに分類して紹介します。
これらはどのような状況下でも、通常の識別子として使用することはできません。
型に関するキーワード
値型や参照型、あるいはデータの性質を定義するためのキーワードです。
| キーワード | 概要 |
|---|---|
bool | 真偽値 (true/false) を表す型 |
byte | 8ビット符号なし整数 |
char | Unicode文字 |
class | クラスを宣言する |
decimal | 高精度の10進浮動小数点数 |
double | 倍精度浮動小数点数 |
enum | 列挙型を宣言する |
float | 単精度浮動小数点数 |
int | 32ビット符号付き整数 |
long | 64ビット符号付き整数 |
object | すべての型のルートとなる基本型 |
sbyte | 8ビット符号付き整数 |
short | 16ビット符号付き整数 |
string | 文字列型 |
struct | 構造体を宣言する |
uint | 32ビット符号なし整数 |
ulong | 64ビット符号なし整数 |
ushort | 16ビット符号なし整数 |
void | 戻り値がないことを示す |
修飾子に関するキーワード
クラス、メソッド、変数の動作やアクセス範囲を制御するためのキーワードです。
| キーワード | 概要 |
|---|---|
abstract | 抽象クラスや抽象メンバーを定義する |
const | 定数を宣言する |
extern | 外部で実装されたメソッドを宣言する |
internal | 同一アセンブリ内からのみアクセス可能にする |
new | インスタンス生成、または継承メンバーの隠蔽 |
override | 基底クラスのメソッドを再定義する |
private | 同一クラス内からのみアクセス可能にする |
protected | 同一クラスまたは派生クラスからアクセス可能にする |
public | どこからでもアクセス可能にする |
readonly | 読み取り専用のフィールドを定義する |
sealed | クラスの継承やメソッドのオーバーライドを禁止する |
static | 静的メンバーを定義する |
virtual | オーバーライド可能なメソッドを定義する |
volatile | フィールドが複数のスレッドによって変更される可能性があることを示す |
ステートメントと制御フロー
プログラムの実行順序を制御するためのキーワードです。
| キーワード | 概要 |
|---|---|
as | 型のキャスト(失敗時にnullを返す) |
base | 親クラスのインスタンスを参照する |
break | ループやswitch文を抜ける |
case | switch文のラベル |
catch | 例外を捕捉する |
continue | ループの次の反復へジャンプする |
default | switch文のデフォルト値、または型の初期値 |
do | do-whileループの開始 |
else | if文の条件が偽の場合の処理 |
finally | 例外の有無にかかわらず実行されるブロック |
for | forループの開始 |
foreach | コレクションの各要素に対するループ |
goto | 指定したラベルへジャンプする |
if | 条件分岐の開始 |
in | foreach内での反復、または参照渡し引数 |
is | 型の互換性をチェックする |
lock | スレッド排他制御を行う |
return | メソッドから値を返し、呼び出し元に戻る |
switch | 多方向分岐の開始 |
this | 現在のインスタンスを参照する |
throw | 例外をスローする |
try | 例外監視ブロックの開始 |
typeof | 型のSystem.Typeオブジェクトを取得する |
using | リソースの破棄を保証する、または名前空間のインポート |
while | 条件が真の間ループする |
コンテキストキーワードの仕組みと注意点
コンテキストキーワードは、「特定の構文上の位置」においてのみ予約語として機能するという特徴を持っています。
これにより、新しいキーワードが言語に追加された際にも、既存のコードでその単語を変数名として使っていた場合に動作が壊れないよう設計されています。
代表的なコンテキストキーワードには以下のものがあります。
var: 暗黙的な型指定の変数宣言時に使用されます。get/set: プロパティのアクセサーを定義する際に使用されます。yield: イテレータブロックで値を返す際に使用されます。await/async: 非同期処理を記述する際に使用されます。partial: クラスやメソッドの定義を分割する際に使用されます。dynamic: 動的型付けを行う際に使用されます。
例えば、var は以下のように振る舞います。
using System;
public class Program
{
public static void Main()
{
// ここでの var はコンテキストキーワード(型推論)
var message = "Hello, World!";
// ここでの var は通常の変数名として機能する(コンテキストキーワードではない)
int var = 100;
Console.WriteLine(message);
Console.WriteLine(var);
}
}
Hello, World!
100
このように、int var = 100; という記述は有効ですが、コードの可読性を著しく低下させるため、避けるのが一般的です。
予約語を識別子として使う方法(逐語的識別子)
どうしても予約語を識別子(変数名、メソッド名など)として使用しなければならない場面があります。
例えば、外部ライブラリとの連携や、自動生成されたコードとの互換性を保つ必要がある場合などです。
C#では、キーワードの前に @(アットマーク)記号を付与することで、そのキーワードを識別子として扱うことができます。
これを「逐語的識別子 (Verbatim Identifiers)」と呼びます。
逐語的識別子の使用例
以下のサンプルコードでは、通常は使用できない class や if を変数名として定義しています。
using System;
public class KeywordTest
{
public static void Main()
{
// @ を付けることで予約語を識別子として利用可能
string @class = "プログラミングクラス";
int @if = 2024;
Console.WriteLine($"classの内容: {@class}");
Console.WriteLine($"ifの内容: {@if}");
// 呼び出す際も @ が必要
DisplayValue(@class);
}
public static void DisplayValue(string text)
{
Console.WriteLine("値: " + text);
}
}
classの内容: プログラミングクラス
ifの内容: 2024
値: プログラミングクラス
注意点として、@ 自体は識別子の名前の一部ではありません。
コンパイルされた際、@class は単なる class という名前の識別子として処理されます。
他の .NET 言語(VB.NET など)からこのアセンブリを参照する場合、その言語側での予約語の扱いによっては、同様の回避策が必要になることがあります。
命名規則とエラーを回避するためのベストプラクティス
予約語の衝突を避け、かつ保守性の高いコードを書くためには、C#の標準的な命名規則に従うことが極めて重要です。
1. 意味のある名前を付ける
単なる @int や @string といった名前ではなく、その変数が何を表しているのかを具体的に示す名前を付けます。
- 不適切な例:
int @for = 10; - 適切な例:
int loopCount = 10;
2. パスカルケースとキャメルケースの使い分け
C#では一般的に、クラス名やメソッド名にはパスカルケース (PascalCase)、ローカル変数や引数名にはキャメルケース (camelCase) を使用します。
- クラス名:
UserAccount - メソッド名:
CalculateTotalAmount - ローカル変数名:
userName
予約語の多くは小文字で構成されているため、パスカルケース(先頭が大文字)を採用するだけで、予約語との衝突は自然に回避されることが多いです。
例えば、class は予約語ですが、Class というクラス名を定義することは可能です(ただし、混同しやすいため推奨はされません)。
3. @ prefix の使用は最小限に留める
@ を使用すれば予約語を変数名にできますが、これはあくまでも「最終手段」です。
コードの読み手にとって、@event という変数が現れると、それが言語仕様のイベントハンドラなのか単なる変数なのかを一瞬で判断しづらくなります。
最新のC#で追加されたキーワード
C#は進化し続けており、比較的新しいバージョンでも新しいキーワードやコンテキストキーワードが追加されています。
これらを知っておくことで、最新の言語機能を活用した効率的な記述が可能になります。
record (C# 9.0)
データ保持に特化したクラスの一種を定義するコンテキストキーワードです。
不変性(イミュータビリティ)を持つオブジェクトを簡潔に記述できます。
init (C# 9.0)
オブジェクトの初期化時のみ値を設定できるプロパティアクセサーです。
nint / nuint (C# 9.0)
プラットフォームのポインタサイズに応じた整数型(ネイティブ整数)を定義します。
required (C# 11)
オブジェクト初期化時にそのプロパティの設定を必須にする修飾子です。
public class Person
{
// C# 11 の required キーワード
public required string Name { get; init; }
public int Age { get; set; }
}
// 使用例
// var p = new Person(); // コンパイルエラー:Nameが未指定
var p = new Person { Name = "田中太郎" }; // 正常
予約語に関連するよくあるエラーと対処法
開発中によく遭遇する予約語関連のトラブルとその解決策をまとめました。
CS0116: 名前空間に型、フィールド、メソッドなどのメンバーを直接含めることはできません
このエラーは、予約語の打ち間違いや、クラスの外部に実行コードを記述してしまった場合に発生することがありますが、稀に予約語を変数名として使おうとした際、コンパイラが「新しい定義が始まった」と勘違いして発生することもあります。
CS1001: 識別子が必要です
int class = 5; のように予約語をそのまま使った場合、コンパイラは「型(int)の後にクラス定義(class)が来るのはおかしい」と判断し、このエラーを出すことがあります。
この場合は、変数名を変更するか、@ を付与することで解決します。
contextual keyword の誤用
例えば、var という名前のクラスを作成してしまった場合、他の場所で var x = 10; と書くと、コンパイラが「型推論のvar」なのか「独自クラスのvar」なのかを判別できなくなり、予期せぬエラーや警告を招くことがあります。
まとめ
C#の予約語は、言語の構造を支える重要な骨組みです。
これらを正しく理解し、適切に避ける(あるいは @ で制御する)ことは、堅牢なプログラムを書くための第一歩となります。
- 予約済みキーワードは、原則として識別子に使用できない。
- コンテキストキーワードは、特定の場所以外では識別子として利用可能だが、混乱を避けるため多用はしない。
- どうしても予約語を名前に使いたい場合は、
@を接頭辞として付与する。 - 最新のC#バージョンでも新しいキーワードが追加されているため、定期的な情報のアップデートが推奨される。
日々の開発においては、予約語を回避するだけでなく、C#の標準的な命名規則(パスカルケースやキャメルケース)を遵守することで、自然とキーワードとの衝突を減らし、読みやすくメンテナンス性の高いコードを維持していきましょう。






