各言語の文字列リテラル: シングルクォート、ダブルクォート、変数展開、エスケープシーケンス (Java, JavaScript, Kotlin, PHP, Python, Ruby)

## 概要

- 各プログラミング言語 (Java, JavaScript, Kotlin, PHP, Python, Ruby) について、シングルクォート (シングル・クォーテーション) やダブルクォート (ダブル・クォーテーション) で囲って文字列を定義する際の、変数展開やエスケープシーケンスについて調べる

## 用語説明

### シングルクォートとダブルクォート

一般的に各プログラミング言語では、文字列リテラルを表現する際に、文字列をシングルクォートまたはダブルクォートで囲む仕様になっていることが多い。

- シングルクォート: 「'」
- ダブルクォート: 「"」

シングルクォート (single quote) はシングルクォーテーション (single quotation)、ダブルクォート (double quote) はダブルクォーテーション (double quotation) と呼ばれることもある。

### 変数展開

所定の記述方法で文字列中に変数名を埋め込むことで、その変数に格納されている値をその箇所に展開することができる機能。

### エスケープシーケンス

改行などの制御文字等を文字列に埋め込むための記述方式。

[エスケープシーケンス \- Wikipedia](https://ja.wikipedia.org/wiki/%E3%82%A8%E3%82%B9%E3%82%B1%E3%83%BC%E3%83%97%E3%82%B7%E3%83%BC%E3%82%B1%E3%83%B3%E3%82%B9)

> エスケープシーケンス (escape sequence) とは、コンピュータシステムにおいて、通常の文字列では表せない特殊な文字や機能を、規定された特別な文字の並びにより表したもの。

[制御文字 \- Wikipedia](https://ja.wikipedia.org/wiki/%E5%88%B6%E5%BE%A1%E6%96%87%E5%AD%97)

> コンピューティングと電気通信において、制御文字（せいぎょもじ、英語: control character）とは、文字コードの規格で定義される文字のうち、ディスプレイ・プリンター・通信装置などに対して、特別な動作（制御）をさせるために使う文字である。制御キャラクタともいい、情報処理用語規格では「制御機能文字」と呼ばれている。

## 各プログラミング言語の仕様

### Java

- 文字列はシングルクォートで囲むことはできない。1文字だけの場合はシングルクォートで囲むことが可能だが、それは String 型ではなく char 型になる
- ダブルクォートで囲まれた文字列は変数展開はしないがエスケープシーケンスが可能
- String.format などで文字列の中に変数展開することが可能

[String \(Java SE 11 & JDK 11 \)](https://docs.oracle.com/javase/jp/11/docs/api/java.base/java/lang/String.html)

> Stringクラスは文字列を表します。 Javaプログラム内の"abc"などのリテラル文字列はすべて、このクラスのインスタンスとして実行されます。

3.10.5. String Literals: [Chapter 3\. Lexical Structure](https://docs.oracle.com/javase/specs/jls/se11/html/jls-3.html#jls-3.10.5)

> A string literal consists of zero or more characters enclosed in double quotes. Characters may be represented by escape sequences (§3.10.6) - one escape sequence for characters in the range U+0000 to U+FFFF, two escape sequences for the UTF-16 surrogate code units of characters in the range U+010000 to U+10FFFF.

3.10.4. Character Literals: [Chapter 3\. Lexical Structure](https://docs.oracle.com/javase/specs/jls/se11/html/jls-3.html#jls-3.10.4)

> A character literal is expressed as a character or an escape sequence (§3.10.6), enclosed in ASCII single quotes. (The single-quote, or apostrophe, character is \u0027.)

動作確認用サンプルコード。

```java
public class Quote {
  public static void main(String[] args) {
    String foo = "Hello";
    String bar = "world";
    System.out.println("Double quote: %s\n%s");
    System.out.println(String.format("Double quote: %s\n%s", foo, bar));
  }
}
```

macOS Mojave + OpenJDK 11.0.2 での実行結果。

```
$ javac Quote.java 

$ java Quote
Double quote: %s
%s
Double quote: Hello
world
```

### JavaScript

- シングルクォートで囲まれた文字列は変数展開はしないがエスケープシーケンスが可能
- ダブルクォートで囲まれた文字列は変数展開はしないがエスケープシーケンスが可能
- グレイヴ・アクセント (バッククォート) で囲まれた文字列は変数展開とエスケープシーケンスが可能

[テキストを扱う — JavaScript での文字列 \- Web 開発を学ぶ \| MDN](https://developer.mozilla.org/ja/docs/Learn/JavaScript/First_steps/Strings)

> JavaScript では、文字列を囲む引用符として、シングルクォーテーションとダブルクォーテーションを使用することができます。

[Template literals \(Template strings\) \- JavaScript \| MDN](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Template_literals)

> Template literals are string literals allowing embedded expressions. You can use multi-line strings and string interpolation features with them. They were called "template strings" in prior editions of the ES2015 specification.

動作確認用サンプルコード。

```js
const foo = 'Hello';
const bar = 'world';
console.log('Single quote: ${foo}\n${bar}');
console.log("Double quote: ${foo}\n${bar}");
console.log(`Grave accent: ${foo}\n${bar}`);
```

macOS Mojave + Node.js 12.8.0 での実行結果。

```
$ node quote.js 
Single quote: ${foo}
${bar}
Double quote: ${foo}
${bar}
Grave accent: Hello
world
```

### Kotlin

- 文字列はシングルクォートで囲むことはできない。1文字だけの場合はシングルクォートで囲むことが可能だが、それは String 型ではなく Char 型になる
- ダブルクォートで囲まれた文字列は変数展開とエスケープシーケンスが可能
- ダブルクォート3つで囲まれた文字列 (raw string) は変数展開が可能だがエスケープシーケンスは使えない

[Basic Types: Numbers, Strings, Arrays \- Kotlin Programming Language](https://kotlinlang.org/docs/reference/basic-types.html)

> Character literals go in single quotes: '1'. Special characters can be escaped using a backslash. The following escape sequences are supported: \t, \b, \n, \r, \', \", \\ and \\\$. To encode any other character, use the Unicode escape sequnce syntax: '\uFF00'.

[Basic Types: Numbers, Strings, Arrays \- Kotlin Programming Language](https://kotlinlang.org/docs/reference/basic-types.html)

> Kotlin has two types of string literals: escaped strings that may have escaped characters in them and raw strings that can contain newlines and arbitrary text. 

[Basic Types: Numbers, Strings, Arrays \- Kotlin Programming Language](https://kotlinlang.org/docs/reference/basic-types.html)

> A raw string is delimited by a triple quote ("""), contains no escaping and can contain newlines and any other characters:

動作確認用サンプルコード。

```kotlin
val foo = "Hello"
val bar = "world"
println("Double quote: ${foo}\n${bar}")
println("""Triple quote: ${foo}\n${bar}""")
```

macOS Mojave + Kotlin 1.3.41 での実行結果。

```
$ kotlinc -script quote.kts 
Double quote: Hello
world
Triple quote: Hello\nworld
```

### PHP

- シングルクォートで囲まれた文字列は未加工のまま
- ダブルクォートで囲まれた文字列は変数展開とエスケープシーケンスが可能

[PHP: 文字列 \- Manual](https://www.php.net/manual/ja/language.types.string.php)

> string は、文字が連結されたものです。PHP では、 文字は 1 バイトと同じです。つまり、256 個の異なる文字を使用可能です。 これは、PHP が Unicode をネイティブにサポートしていないことも意味します。

[PHP: 文字列 \- Manual](https://www.php.net/manual/ja/language.types.string.php)

> 文字列を指定する最も簡単な方法は、引用符 (文字 ') で括ることです。
> 引用符をリテラルとして指定するには、バックスラッシュ (\\) でエスケープする必要があります。 バックスラッシュをリテラルとして指定するには、二重 (\\\\) にします。 それ以外の場面で登場するバックスラッシュは、すべてバックスラッシュそのものとして扱われます。 つまり、\r や \n といったおなじみのエスケープシーケンスを書いても特別な効果は得られず、 書いたままの形式で出力されます。

[PHP: 文字列 \- Manual](https://www.php.net/manual/ja/language.types.string.php)

> 文字列が二重引用符 (") で括られた場合、 PHP は、以下のエスケープシーケンスを特殊な文字として解釈します。

[PHP: 文字列 \- Manual](https://www.php.net/manual/ja/language.types.string.php)

> スクリプトが二重引用符で括られるかヒアドキュメントで指定された場合、 その中の変数はパースされます。

動作確認用サンプルコード。

```
<?php
$foo = 'Hello';
$bar = 'world';
echo 'Single quote: {$foo}\n{$bar}', "\n";
echo "Double quote: {$foo}\n{$bar}", "\n";
```

macOS Mojave + PHP 7.3.7 での実行結果。

```
$ php quote.php 
Single quote: {$foo}\n{$bar}
Double quote: Hello
world
```

### Python

- シングルクォートで囲まれた文字列は f-string にて変数展開とエスケープシーケンスが可能
- ダブルクォートで囲まれた文字列は f-string にて変数展開とエスケープシーケンスが可能

[組み込み型 — Python 3\.7\.4 ドキュメント](https://docs.python.org/ja/3.7/library/stdtypes.html#text-sequence-type-str)

> Python のテキストデータは str オブジェクト、すなわち 文字列 として扱われます。文字列は Unicode コードポイントのイミュータブルな シーケンス です。文字列リテラルには様々な記述方法があります:
> 
> ・シングルクォート: '"ダブル" クォートを埋め込むことができます'
> ・ダブルクォート: "'シングル' クォートを埋め込むことができます"。
> ・三重引用符: '''三つのシングルクォート''', """三つのダブルクォート"""
> 
> 三重引用符文字列は、複数行に分けることができます。関連付けられる空白はすべて文字列リテラルに含まれます。
> 単式の一部であり間に空白のみを含む文字列リテラルは、一つの文字列リテラルに暗黙に変換されます。つまり、("spam " "eggs") == "spam eggs" です。

[2\. 字句解析 — Python 3\.7\.4 ドキュメント](https://docs.python.org/ja/3.7/reference/lexical_analysis.html#strings)

> これらの型のリテラルは、対応する一重引用符 (') または二重引用符 (") で囲われます。また、対応する三連の一重引用符や二重引用符で囲うこともできます (通常、三重クオート文字列: triple-quoted string と呼ばれます)。バックスラッシュ (\\) 文字で、本来特別な意味を持つ文字、例えば改行文字、バックスラッシュ自身、クオート文字などを、エスケープできます。

[2\. 字句解析 — Python 3\.7\.4 ドキュメント](https://docs.python.org/ja/3.7/reference/lexical_analysis.html#f-strings)

> フォーマット済み文字列リテラル（ formatted string literal ）または f-string は、接頭辞 'f' または 'F' の付いた文字列リテラルです。これらの文字列には、波括弧 {} で区切られた式である置換フィールドを含めることができます。他の文字列リテラルの場合は内容が常に一定で変わることが無いのに対して、フォーマット済み文字列リテラルは実行時に式として評価されます。

動作確認用サンプルコード。

```py
foo = 'Hello'
bar = 'world'
print(f'Single quote: {foo}\n{bar}')
print(f"Double quote: {foo}\n{bar}")
print(f'''Triple single quote: {foo}\n{bar}''')
print(f"""Triple double quote: {foo}\n{bar}""")
```

macOS Mojave + Python 3.7.4 での実行結果。

```
$ python quote.py
Single quote: Hello
world
Double quote: Hello
world
Triple single quote: Hello
world
Triple double quote: Hello
world
```

### Ruby

- シングルクォートで囲まれた文字列は未加工のまま
- ダブルクォートで囲まれた文字列は変数展開とエスケープシーケンスが可能

[リテラル \(Ruby 2\.6\.0\)](https://docs.ruby-lang.org/ja/latest/doc/spec=2fliteral.html)

> 文字列はダブルクォートまたはシングルクォートで囲まれています。 ダブルクォートで囲まれた文字列ではバックスラッシュ記法と式展開(後述)が有効になります。 シングルクォートで囲まれた文字列では、 \\\\ (バックスラッシュそのもの)と \' (シングルクォート) を除いて文字列の中身の解釈は行われません。 シングルクォートで囲まれた文字列では行末の \ は \ そのものとして解釈されます。

[リテラル \(Ruby 2\.6\.0\)](https://docs.ruby-lang.org/ja/latest/doc/spec=2fliteral.html)

> ダブルクォート(")で囲まれた文字列式、コマンド文 字列および正規表現の中では#{式}という形式で式 の内容(を文字列化したもの)を埋め込むことができます。式が変数 記号(\$,@)で始まる変数の場合には {}を省略して、#変数名という形式で も展開できます。文字#に続く文字が {,$,@でなければ、その まま文字#として解釈されます。明示的に式展開を止 めるには#の前にバックスラッシュを置きます。

動作確認用サンプルコード。

```rb
foo = 'Hello'
bar = 'world'
puts 'Single quote: #{foo}\n#{bar}'
puts "Double quote: #{foo}\n#{bar}"
```

macOS Mojave + Ruby 2.6.3 での実行結果。

```
$ ruby quote.rb 
Single quote: #{foo}\n#{bar}
Double quote: Hello
world
```