Xcode
Swift

【Swift】文字列連結のビルド時間と処理時間

Swiftで文字列を連結するにはいくつかやり方はありますが、どのやり方が最適なのか気になったのでビルド時間と処理時間を比較してみました。

まずは文字列連結の実装です。
今回は以下の4パターンを検証します。

var text: String?
let sex = "男"
let picture = "写真"
let number = "三"
let verb = "見た"

// + 演算子を使う方法
func join1() {
    text = "私は、その" + sex + "の" + picture + "を" + number + "葉、" + verb + "ことがある。"
}

// 文字列に変数の値を埋め込む方法
func join2() {
    text = "私は、その\(sex)の\(picture)を\(number)葉、\(verb)ことがある。"
}

// appendを使う方法
func join3() {
    var str = "私は、その"
    str.append(sex)
    str.append("の")
    str.append(picture)
    str.append("を")
    str.append(number)
    str.append("葉、")
    str.append(verb)
    str.append("ことがある。")
    text = str
}

// String(format:)を使う方法
func join4() {
    text = String(format: "私は、その%@の%@を%@葉、%@ことがある。", sex, picture, number, verb)
}

これを BuildTimeAnalyzer-for-Xcode を使ってビルド時間の計測を行います。
結果は以下のようになりました。
スクリーンショット 2018-03-14 22.01.19.png

「String(format:)を使う方法」 が一番速く、「文字列に変数の値を埋め込む方法」が一番遅いようです。

では処理時間はどうでしょうか?
上記のメソッド上から順に以下のような結果になりました。

0.00344204902648926
0.000853061676025391
0.000445008277893066
0.00658690929412842

「String(format:)を使う方法」 が一番遅く、「appendを使う方法」が一番速いようです。

上記の実装例では、文字列連結に使う変数が全て String でしたが、 String 以外が含まれている場合も見てみましょう。
上記の実装例の let number = "三" を Int に変えます。

var text: String?
let sex = "男"
let picture = "写真"
let number = 3
let verb = "見た"
let strings = ["1", "2", "3", "4", "5"]

override func viewDidLoad() {
    super.viewDidLoad()
    join1()
    join2()
    join3()
    join4()
}

// + 演算子を使う方法
func join1() {
    text = "私は、その" + sex + "の" + picture + "を" + String(number) + "葉、" + verb + "ことがある。"
}

// 文字列に変数の値を埋め込む方法
func join2() {
    text = "私は、その\(sex)の\(picture)を\(number)葉、\(verb)ことがある。"
}

// appendを使う方法
func join3() {
    var str = "私は、その"
    str.append(sex)
    str.append("の")
    str.append(picture)
    str.append("を")
    str.append(String(number))
    str.append("葉、")
    str.append(verb)
    str.append("ことがある。")
    text = str
}

// String(format:)を使う方法
func join4() {
    text = String(format: "私は、その%@の%@を%i葉、%@ことがある。", sex, picture, number, verb)
}

スクリーンショット 2018-03-14 23.06.13.png

相変わらず「String(format:)を使う方法」が一番早いですが、 StringInt が混ざっている場合だと「+ 演算子を使う方法」が一番遅くなりました。
処理速度は以下のようになりました。

0.0204509496688843
0.00079500675201416
0.000352025032043457
0.00585699081420898

「+ 演算子を使う方法」 が一番遅く、「appendを使う方法」が一番速いようです。

まとめ

これらの結果から、ビルド時間と処理速度を重視するなら「appendを使う方法」が一番バランスが良さそうですが、実装例を見ても分かるようにコードが冗長で見づらいという難点があります。

ビルド時間を最優先する場合は「String(format:)を使う方法」が良さそうです。
ただし、Objective-Cに馴染みのある人ならそこまで抵抗ないかもしれませんが、Swiftで 「String(format:) を使うのは好みがあるかもしれませんね。

ビルド時間に悩んでいないうちは「+ 演算子を使う方法」や「文字列に変数の値を埋め込む方法」を使っても良いですが、この2つは String だけの場合と、複数の型が混合する場合とで使い分けるのが良さそうです。

Swiftの文字列連結の方法はいくつかありますが、この方法が最適!というものはなく、プロジェクトの状況や実装内容によってケースバイケースということのようでした。