JavaScriptで変数を展開した文字列を作成する時、+
で文字列連結をしていましたがES2015(ES6)からは``
(バッククォート)で囲うテンプレート構文(Template literal)で書くことができるようです。
※ IEやAndroidでは未対応なブラウザもあるようなので、WEBサイト制作とかの場合はまだバベる必要がありそうです。
ブラウザ実装状況: テンプレート文字列 - JavaScript | MDN
テンプレート構文(Template literal)による文字列中での変数展開
var val = "JavaScript" // 今までのやり方 var str1 = "Hello " + val + "!" // => Hello JavaScript! // テンプレート構文 var str2 = `Hello ${val}!` // => Hello JavaScript!
文字列中で変数を展開させるプレースホルダーは${...}
の形式で記述します。
プレースホルダー内で計算
プレースホルダー${...}
内では計算や関数を呼ぶこともできるようです。
var a = 3, b = 5 console.log( `a + b = ${a + b}, a * 2 + b = ${a * 2 + b}` ) // => a + b = 8, a * 2 + b = 11 function sub(a, b) { return a - b } console.log( `a - b = ${sub(a, b)}` ) // => a - b = -2
同期的なことはできない
function timer() { setTimeout(()=> { return 'timeout!' }, 100) } console.log( `set timer ... ${timer()}` ) // => set timer ... undefined
改行
テンプレート構文(Template literal)内では改行がそのまま改行として扱われる。(\n
も使える)
var str1 = "Hello\nJavaScript" // ↓ var str2 = `Hello JavaScript` var str3 = `Hello\nJavaScript` console.log(str2) // Hello // JavaScript console.log(str3) // Hello // JavaScript
コード上で改行だけさせたい時
見やすくするとかでコード上でだけ改行させたいような場合
var tag1 = "<div>" + "<p>Hello JavaScript</p>" + "</div>" console.log(tag1) // => <div><p>Hello JavaScript</p></div> var tag2 = "<div>\ <p>Hello JavaScript</p>\ </div>" console.log(tag2) // => <div><p>Hello JavaScript</p></div>
テンプレート構文(Template literal)では改行はそのまま改行になってしまうので、改行前に\
を付けて改行すればOK。(以前の方法と同じ)
var tag = `<div>\ <p>Hello JavaScript</p>\ </div>` console.log(tag) // => <div><p>Hello JavaScript</p></div>
エスケープ
\
や\n
をそのまま表示したいような場合、テンプレート構文(Template literal)ではString.raw
を使う。(\
でエスケープする今までどおりの方法でもOK)
var str1 = "Hello\\nJava\\Script" // ↓ var str2 = String.raw`Hello\nJava\Script` var str3 = `Hello\\nJava\\Script` console.log(str1 === str2, str1 === str3, str2 === str3) // => true true true console.log(str2) // => Hello\nJava\Script
String.raw内でもプレースホルダー${...}
は展開される
var name = "アシリパ" String.raw`こんにちわ\n${name}さん` // => こんにちは\nアシリパさん
${...}
をそのまま表示させたい場合はString.raw
を使わずに\${...}
又は$\{...}
とエスケープする
var name = "アシリパ" `こんにちは\\n\${name}さん` // => こんにちは\n${name}さん `こんにちは\\n$\{name}さん` // => こんにちは\n${name}さん
String.raw
を使うと\${...}
、$\{...}
の\
が出力されてしまう
var name = "アシリパ" String.raw`こんにちは\n\${name}さん` // => こんにちは\n\${name}さん String.raw`こんにちは\n$\{name}さん` // => こんにちは\n$\{name}さん
String.raw``のトラップ
テキストの最後に\
を出力したい場合String.raw
だと最後の`
をエスケープしていると判断されエラーになるので注意が必要
"Hello\\nJava\\Script\\" // => Hello\nJava\Script\ `Hello\\nJava\\Script\\` // => Hello\nJava\Script\ String.raw`Hello\nJava\Script\` // => Error
String.raw
を使って最後に\
を出力するには\
を文字列結合するか、プレースホルダーで追加すればOK
String.raw`Hello\nJava\Script` + "\\" // => Hello\nJava\Script\ var suffix = "\\" String.raw`Hello\nJava\Script${suffix}` // => Hello\nJava\Script\
エスケープして表示したい時は今までどおりの\
でエスケープする方法の方が良さそうかも…
String.raw()
静的メソッドである
String.raw()
は、文字列リテラルのための Python のr
プレフィックスや C# の@
プレフィックスのような template strings のタグ関数です。この関数は、template strings の生の文字列形式を取得するために使用されます。
出典: String.raw() - JavaScript | MDN
String.raw
は関数なので、function``
で関数が実行される。
テンプレート構文(Template literal)で実行された関数に渡される引数
テンプレート構文(Template literal)で渡される第一引数は文字列をプレースホルダーで分割したArray-likeな変更不可能なオブジェクト、第二引数以降はプレースホルダーに入る値。値は計算された状態で関数に渡されるっぽい。
var a = 5, b = 10 function tag(strings, ...values) { console.log(strings) // 変更不可オブジェクト console.log(values) // プレースホルダーの値 return strings } var str1 = tag`Hello${a+b}Java${a-b}script` // strings: [ 'Hello', 'Java', 'script' ] // vales: [ 15, -5 ] var str2 = tag`Hello${b-a}Java${a*b}script` // strings: [ 'Hello', 'Java', 'script' ] // values: [ 5, 50 ] console.log(str1 === str2) // true console.log(typeof(str1)) // 'object' // 変更しようとするとエラーになる str1[1] = 'World' // => TypeError: Cannot assign to read only property delete str1[2] // => TypeError: Cannot delete property str1.push('!') // => TypeError: Cannot add property
公式を見るとクロージャーな関数を返すとか色々な使い方ができるっぽいけど、実際に使う場面がイマイチピンこない...
はてなブログのJavaScriptいい感じにシンタックスハイライトされなくて辛い…
[参考]
マークダウンで`
バッククォートをcodeで囲って書くTips

初めてのJavaScript 第3版 ―ES2015以降の最新ウェブ開発
- 作者: Ethan Brown,武舎広幸,武舎るみ
- 出版社/メーカー: オライリージャパン
- 発売日: 2017/01/20
- メディア: 単行本(ソフトカバー)
- この商品を含むブログを見る