UnityでのStringの連結について

Unity
スポンサーリンク

はじめに

UnityでStringの連結する際の連結方法によって速度の違いがあるかどうか検証してみました。

※あくまで一例なので環境などにより速度が変わる場合があります。

環境

  • Unity 2021.3.10f1
  • .NET Standard 2.1
  • C# 8.0

公式ドキュメント

Unity - Scripting API: String
複数の文字列を連結する方法 (C# ガイド) - C#
C# で文字列を連結する方法は複数あります。 各選択のオプションと、それを選ぶ理由も示します。

Stringの連結

各ケースで10000回forでループさせ検証しています。

表示させる文章「19日の天気は晴れ、最高気温は29.5、最低気温は26.4の予報です。」

field(変数宣言部)

enum Wather
{
    晴れ,
    曇り
}

int day = 19;
Wather weather = Wather.晴れ;
float maxTemp = 29.5f;
float minTemp = 26.4f;

Case1ー「string.Format」を使った方法

msg1 = string.Format("{0}日の天気は{1}、最高気温は{2}、最低気温は{3}の予報です。", day, weather, maxTemp, minTemp);
StopwatchSelf(ms)GC Alloc
21.67ms24.13ms2.4MB
5回の平均

Case2ー「+」を使った方法

msg1 = day + "日の天気は" + weather + "、最高気温は" + maxTemp + "、最低気温は" + minTemp + "の予報です。";
StopwatchSelf(ms)GC Alloc
19.77ms23.46ms3.0MB
5回の平均

Case3ー「StringBuilder」を使った方法(「+」を使った方法)

sb.Append(day + "日の天気は" + weather + "、最高気温は" + maxTemp + "、最低気温は" + minTemp + "の予報です。");
msg1 = sb.ToString();
StopwatchSelf(ms)GC Alloc
25.62ms30.87ms6.1MB
5回の平均

Case3-1ー「StringBuilder」を使った方法(分けて使った方法)

StringBuilder sb = new StringBuilder();
sb.Append(day);
sb.Append("日の天気は");
sb.Append(weather);
sb.Append("、最高気温は");
sb.Append(maxTemp);
sb.Append("、最低気温は");
sb.Append(minTemp);
sb.Append("の予報です。");
msg1 = sb.ToString();
StopwatchSelf(ms)GC Alloc
27.12ms29.82ms5.6MB
5回の平均

Case3-2ー「StringBuilder」を使った方法(つなげて使った方法)

StringBuilder sb = new StringBuilder();
sb.Append(day).Append("日の天気は").Append(weather).Append("、最高気温は").Append(maxTemp).Append("、最低気温は").Append(minTemp).Append("の予報です。");
msg1 = sb.ToString();
StopwatchSelf(ms)GC Alloc
24.88ms31.05ms5.6MB
5回の平均

Case4ー文字列補間式を使った方法

msg1 = $"{day}日の天気は{weather}、最高気温は{maxTemp}、最低気温は{minTemp}の予報です。";
StopwatchSelf(ms)GC Alloc
20.33ms26.33ms2.4MB
5回の平均

Case4-1ー文字列補間式を使った方法(「.ToString」を使った方法)

msg1 = $"{day.ToString()}日の天気は{weather.ToString()}、最高気温は{maxTemp.ToString()}、最低気温は{minTemp.ToString()}の予報です。";
StopwatchSelf(ms)GC Alloc
19.74ms24.31ms3.0MB
5回の平均

まとめ

早いのは「Case2」、「Case4-1」となりました。

「Case4-1」は早いのですが冗長な文になって可読性が下がっているので実用的なのは「Case2」、「Case4」かなと筆者的には思いました。

全文

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.Text;
using UnityEngine.Profiling;
using System;

public class test : MonoBehaviour
{
    enum Wather
    {
        晴れ,
        曇り
    }

    int day = 19;
    Wather weather = Wather.晴れ;
    float maxTemp = 29.5f;
    float minTemp = 26.4f;

    void Start()
    {
        //ケース1
        System.Diagnostics.Stopwatch stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case1();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);

        //ケース2
        stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case2();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);

        //ケース3
        stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case3();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);

        //ケース3-1
        stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case3_1();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);

        //ケース3-2
        stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case3_2();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);

        //ケース4
        stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case4();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);

        //ケース4-1
        stopwatch = new System.Diagnostics.Stopwatch();
        stopwatch.Start();

        Case4_1();

        stopwatch.Stop();
        Debug.Log(stopwatch.Elapsed);
    }

    /// <summary>
    /// ケース1
    /// </summary>
    void Case1()
    {
        Profiler.BeginSample("1");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            msg1 = string.Format("{0}日の天気は{1}、最高気温は{2}、最低気温は{3}の予報です。", day, weather, maxTemp, minTemp);
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }

    /// <summary>
    /// ケース2
    /// </summary>
    void Case2()
    {
        Profiler.BeginSample("2");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            msg1 = day + "日の天気は" + weather + "、最高気温は" + maxTemp + "、最低気温は" + minTemp + "の予報です。";
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }

    /// <summary>
    /// ケース3
    /// </summary>
    void Case3()
    {
        Profiler.BeginSample("3");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            StringBuilder sb = new StringBuilder();
            sb.Append(day + "日の天気は" + weather + "、最高気温は" + maxTemp + "、最低気温は" + minTemp + "の予報です。");
            msg1 = sb.ToString();
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }

    /// <summary>
    /// ケース3-1
    /// </summary>
    void Case3_1()
    {
        Profiler.BeginSample("3-1");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            StringBuilder sb = new StringBuilder();
            sb.Append(day);
            sb.Append("日の天気は");
            sb.Append(weather);
            sb.Append("、最高気温は");
            sb.Append(maxTemp);
            sb.Append("、最低気温は");
            sb.Append(minTemp);
            sb.Append("の予報です。");
            msg1 = sb.ToString();
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }

    /// <summary>
    /// ケース3-2
    /// </summary>
    void Case3_2()
    {
        Profiler.BeginSample("3-2");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            StringBuilder sb = new StringBuilder();
            sb.Append(day).Append("日の天気は").Append(weather).Append("、最高気温は").Append(maxTemp).Append("、最低気温は").Append(minTemp).Append("の予報です。");
            msg1 = sb.ToString();
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }

    /// <summary>
    /// ケース4
    /// </summary>
    void Case4()
    {
        Profiler.BeginSample("4");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            msg1 = $"{day}日の天気は{weather}、最高気温は{maxTemp}、最低気温は{minTemp}の予報です。";
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }

    /// <summary>
    /// ケース4-1
    /// </summary>
    void Case4_1()
    {
        Profiler.BeginSample("4-1");

        string msg1 = "";
        for (int i = 0; i < 10000; i++)
        {
            msg1 = "";
            msg1 = $"{day.ToString()}日の天気は{weather.ToString()}、最高気温は{maxTemp.ToString()}、最低気温は{minTemp.ToString()}の予報です。";
        }
        Debug.Log(msg1);

        Profiler.EndSample();
    }
}

コメント

タイトルとURLをコピーしました