2018年5月7日月曜日
[MQL4] string と datetime 型の相互変換方法5種
[string と datetime の加算演算は strict モードかどうかで動作が変わる](https://strategyofc.blogspot.com/2018/05/mql4-string-datetime-strict.html) に書いたように datetime の string への変換は明示的に行ったほうが良いと思います。 基本的には、MQL4 の固定フォーマット "yyyy.mm.dd hh:mi" を使うのが簡単ですが、独自のフォーマットで出力することも可能です ### datetime を string にする方法1 (固定フォーマット) [TimeToString()](https://docs.mql4.com/convert/timetostr) もしくは [TimeToStr()](https://docs.mql4.com/convert/timetostr) を使うのが簡単です 。 ```mq4 datetime now = TimeLocal(); Print(TimeToString(now, TIME_DATE)); // 2018.05.04 Print(TimeToString(now, TIME_DATE|TIME_MINUTES)); // 2018.05.04 15:51 Print(TimeToString(now, TIME_DATE|TIME_SECONDS)); // 2018.05.04 15:51:12 Print(TimeToString(now, TIME_MINUTES)); // 15:51 Print(TimeToString(now, TIME_SECONDS)); // 15:51:12 ``` ### datetime を string にする方法2 (任意フォーマット) 上記の方法では特定のフォーマットに決まってしまいますが、任意のフォーマットにしたい場合は、一度 [MqlDateTime](https://docs.mql4.com/constants/structures/mqldatetime) に変換して[StringFormat()](https://docs.mql4.com/convert/stringformat) で整形すると良いでしょう。 ```mq4 datetime now = TimeLocal(); MqlDateTime now_struct; TimeToStruct(now, now_struct); Print(StringFormat("%4d/%02d/%02d %02d:%02d", now_struct.year, now_struct.mon, now_struct.day, now_struct.hour, now_struct.min)); // 2018/05/04 16:03 ``` ### datetime を string にする方法3 (任意フォーマット) もしくは [TimeXXX](https://docs.mql4.com/dateandtime) 関数を使って、datetime を直接各値に変換することも可能です。 ```mq4 datetime now = TimeLocal(); Print(StringFormat("%4d/%02d/%02d %02d:%02d", TimeYear(now), TimeMonth(now), TimeDay(now), TimeHour(now), TimeMinute(now))); // 2018/05/04 16:42 ``` 一般的に、都度関数呼び出しの方がパフォーマンスが悪くなることが多いです。 ただ、MQL4 の仕様でどうなっているのかはわかりません 。 ### string を datetime にする方法1 (固定文字列) 先頭に 'D' をつけたシングルクォートで囲まれた文字列は datetime とみなされます。 ```mq4 datetime date1 = D'2018.05.04 07:23:01'; // こちらはコンパイルエラー datetime date2 = D'This is not a date string'; ``` > 参考 > > [Datetime Type - Integer Types - Data Types - Language Basics - MQL4 Reference](https://docs.mql4.com/basis/types/integer/datetime) ### string を datetime にする方法2 動的な string を datetime に変換する場合は、 [StringToTime()](https://docs.mql4.com/convert/stringtotime) もしくは [StrToTime()](https://docs.mql4.com/convert/strtotime) が使えます 。 ```mq4 string date_string = "1970.01.01 01:00:00"; datetime date = StringToTime(date_string); printf("%llu", date); // 3600 Print(TimeToString(date, TIME_DATE|TIME_SECONDS)); // 1970.01.01 01:00:00 ``` > 参考 > > [[MQL4] datetime を long にキャストすると 1970/1/1 からの秒になる | Strategy of C](https://strategyofc.blogspot.com/2018/05/mql4-datetime-long-197011.html) この関数、下記のように多少フォーマットが異なっていても動作するようです。 しかし、公式のドキュメントに記述が無いので、使用する場合は慎重に確認した方が良いでしょう。 ```mq4 `highlight: 1; string date_string = "1970/01/01 01:00:00"; datetime date = StringToTime(date_string); printf("%llu", date); // 3600 Print(TimeToString(date, TIME_DATE|TIME_SECONDS)); // 1970.01.01 01:00:00 ``` なお、以下のように日付ではない文字列を変換した場合、実行時の日付、もしくは日時が入るようです 。 時刻が入るかどうかは文字列によるようで、動作が微妙です。公式のドキュメントにも記述はありません。 想定外の文字列が入力される可能性のある系では、気をつけた方が良いでしょう。 ```mq4 string no_date_string = "This is not a date string"; datetime date = StringToTime(no_date_string); Print(TimeToString(date, TIME_DATE|TIME_SECONDS)); // 実行時の日時? ```。