逐語的テキスト - 変数、属性、文字列リテラルの @

特殊文字 @ は、逐語的識別子として機能します。 これは次の目的に使用できます。

  1. C# のキーワードを識別子として使用できるようにする。 コード要素のプレフィックスとして @ 文字を使用すると、その要素はC# のキーワードではなく、識別子としてコンパイラに解釈されます。 次の例では、@ 文字を使用して、for ループで使用する for という識別子を定義しています。

    string[] @for = { "John", "James", "Joan", "Jamie" };
    for (int ctr = 0; ctr < @for.Length; ctr++)
    {
       Console.WriteLine($"Here is your gift, {@for[ctr]}!");
    }
    // The example displays the following output:
    //     Here is your gift, John!
    //     Here is your gift, James!
    //     Here is your gift, Joan!
    //     Here is your gift, Jamie!
    
  2. 文字列リテラルを逐語的に解釈することを示す。 このインスタンス内の @ 文字は、逐語的文字列リテラルを定義します。 単純なエスケープ シーケンス (バック スラッシュの "\\" など)、16 進数のエスケープ シーケンス (大文字 A の "\x0041" など)、Unicode のエスケープ シーケンス (大文字 A の "\u0041" など) は、リテラルに解釈されます。 引用符のエスケープ シーケンス ("") だけは、リテラルに解釈されません。1 個の二重引用符が生成されます。 また、逐語的な補間文字列の場合、中かっこエスケープ シーケンス ({{}}) は文字どおり解釈されません。単一の中かっこ文字が生成されます。 次の例では、2 つの同じファイル パスを定義しています。一方は通常の文字列リテラルを使用して、もう一方は 逐語的文字列リテラルを使用して定義しています。 これは、逐語的文字列リテラルの一般的な用途の 1 つです。

    string filename1 = @"c:\documents\files\u0066.txt";
    string filename2 = "c:\\documents\\files\\u0066.txt";
    
    Console.WriteLine(filename1);
    Console.WriteLine(filename2);
    // The example displays the following output:
    //     c:\documents\files\u0066.txt
    //     c:\documents\files\u0066.txt
    

    次の例は、同じ文字シーケンスを通常の文字列リテラルと 逐語的文字列リテラルで定義した場合の結果を示したものです。

    string s1 = "He said, \"This is the last \u0063hance\x0021\"";
    string s2 = @"He said, ""This is the last \u0063hance\x0021""";
    
    Console.WriteLine(s1);
    Console.WriteLine(s2);
    // The example displays the following output:
    //     He said, "This is the last chance!"
    //     He said, "This is the last \u0063hance\x0021"
    
  3. 名前の競合がある場合に、コンパイラが属性を区別できるようにする。 属性は Attribute の派生クラスです。 通常、その型の名前には Attribute サフィックスが含まれます。これは、コンパイラがその規則を強制していない場合でも同様です。 そのため属性は、完全な型名 (たとえば、[InfoAttribute]) か、短縮名 (たとえば、[Info]) によってコード内から参照できます。 ただし、短縮された 2 つの属性型名が同じである場合、一方の型名に Attribute サフィックスが含まれていて、もう一方に含まれていないと、名前の競合が発生します。 たとえば、次のコードでは、InfoInfoAttribute のどちらの属性が Example クラスに適用されるかをコンパイラが判断できないため、コンパイルが失敗します。 詳細については、CS1614 を参照してください。

    using System;
    
    [AttributeUsage(AttributeTargets.Class)]
    public class Info : Attribute
    {
       private string information;
    
       public Info(string info)
       {
          information = info;
       }
    }
    
    [AttributeUsage(AttributeTargets.Method)]
    public class InfoAttribute : Attribute
    {
       private string information;
    
       public InfoAttribute(string info)
       {
          information = info;
       }
    }
    
    [Info("A simple executable.")] // Generates compiler error CS1614. Ambiguous Info and InfoAttribute.
    // Prepend '@' to select 'Info' ([@Info("A simple executable.")]). Specify the full name 'InfoAttribute' to select it.
    public class Example
    {
       [InfoAttribute("The entry point.")]
       public static void Main()
       {
       }
    }
    

関連項目