#環境
Unity5.6.1f1
#概要
スマホでも早くなるのかテスト
結果、自分のスマホなら早くなりました。
#プログラム
using System.Collections.Generic;
using System.Text;
using UnityEngine;
using UnityEngine.UI;
using System.Threading;
public class TestParallelFor : MonoBehaviour
{
[SerializeField] private Button _button = null; //切り替えボタン
[SerializeField] private Text _text = null; //時間表示
class ThreadParam
{
public Thread thread;
// public ManualResetEvent activeEvent;
// public ManualResetEvent finishEvent;
//AutoResetEventはWaitOneでシグナル(Set)になるまで待機した後、勝手に非シグナル(Reset)になる
public AutoResetEvent activeEvent;
public AutoResetEvent finishEvent;
public StringBuilder str;
public int value;
}
private List<ThreadParam> _threadParams = new List<ThreadParam>();
private bool _isParallel = false;
private const int _threadCount = 10;
private const int _loopCount = 1000000;
private void Start()
{
_isParallel = false;
OnButtonClick( _button );
_button.onClick.AddListener( () => OnButtonClick( _button ) );
for( int i = 0; i < _threadCount; i++ )
{
var param = new ThreadParam();
param.thread = new Thread( ThreadFunc );
// param.activeEvent = new ManualResetEvent( false ); //寝かせておく
// param.finishEvent = new ManualResetEvent( false ); //寝かせておく
param.activeEvent = new AutoResetEvent( false ); //寝かせておく
param.finishEvent = new AutoResetEvent( false ); //寝かせておく
param.str = new StringBuilder( 64 );
_threadParams.Add( param );
param.thread.IsBackground = true;
param.thread.Start( param );
}
}
private void OnApplicationQuit()
{
OnDestroy();
}
private void OnDestroy()
{
for( int i = 0; i < _threadParams.Count; i++ )
{
var param = _threadParams[ i ];
if( param.thread == null )
continue;
param.thread.Abort();
}
_threadParams.Clear();
}
private void OnButtonClick( Button button )
{
_isParallel = ( _isParallel == true ) ? false : true;
button.GetComponentInChildren<Text>().text = ( _isParallel == true ) ? "Change Single" : "Change Parallel";
}
private void Update()
{
Debug.Log( "Start" );
var startTime = Time.realtimeSinceStartup;
if( _isParallel == true )
Parallel();
else
Single();
var elapsedTime = Time.realtimeSinceStartup - startTime;
_text.text += ":" + elapsedTime.ToString();
Debug.Log( "Finish" );
}
private void Single()
{
int value = 0;
for( int i = 0; i < _threadParams.Count; i++ )
{
var param = _threadParams[ i ];
Task( param );
value += param.value;
}
_text.text = ( value / _loopCount / _threadCount ).ToString();
}
private void Parallel()
{
//parallel
for( int i = 0; i < _threadParams.Count; i++ )
{
var param = _threadParams[ i ];
param.activeEvent.Set();
}
//finish sync
int value = 0;
for( int i = 0; i < _threadParams.Count; i++ )
{
var param = _threadParams[ i ];
param.finishEvent.WaitOne();
// param.finishEvent.Reset();
value += param.value;
}
_text.text = ( value / _loopCount ).ToString();
}
private void ThreadFunc( object obj )
{
var param = (ThreadParam)obj;
while( true )
{
param.activeEvent.WaitOne();
// param.activeEvent.Reset();
Task( param );
param.finishEvent.Set();
}
}
private void Task( ThreadParam param )
{
param.value = 0;
for( int i = 0; i < _loopCount; i++ )
{
param.value++;
}
param.str.Length = 0;//.Remove( 0, param.str.Length );
param.str.Append( "Task:" ).Append( param.thread.ManagedThreadId );
// Debug.Log( param.str.ToString() );
}
}