MQL4の配列関数を体系的にまとめました。ArrayResize()による動的配列のサイズ変更、ArrayCopy()による配列コピー、ArraySort()によるソート、ArrayMaximum()・ArrayMinimum()による最大値・最小値のインデックス検索、ArrayInitialize()による初期化、ArrayRange()・ArraySize()によるサイズ取得、ArraySetAsSeries()による時系列インデックス設定まで、MT4 EA開発に必要な配列操作のすべてをコード付きで解説します。
MQL4とMQL5の配列関数の違い
| 機能 | MQL4 | MQL5 |
|---|---|---|
| 基本関数 | ほぼ同じ | ほぼ同じ |
| ArraySort | 第2-4引数あり(count, start, direction) | 引数は配列のみ(昇順固定) |
| ArrayMaximum/Minimum | start, count引数あり | start, count引数あり |
| ArrayCopy | 同じ | 同じ |
| 時系列配列 | Close[], Open[], High[], Low[] | CopyClose()等で取得 |
MQL4の配列は静的配列(サイズ固定)と動的配列(サイズ可変)の2種類があります。double arr[100];は静的、double arr[];は動的です。動的配列はArrayResize()でサイズを変更でき、EA開発では動的配列の使用が一般的です。
MQL4の配列は静的配列(サイズ固定)と動的配列(サイズ可変)の2種類があります。double arr[100];は静的、double arr[];は動的です。動的配列はArrayResize()でサイズを変更でき、EA開発では動的配列の使用が一般的です。
ArrayResize — 動的配列のサイズ変更
int ArrayResize(
void& array[], // 対象配列
int new_size, // 新しいサイズ
int reserve_size = 0 // 予約サイズ(パフォーマンス用)
);
// 戻り値: 新しいサイズ、失敗時は-1void DynamicArrayExample()
{
double prices[];
// サイズ0の状態から動的に拡張
ArrayResize(prices, 0);
// データを追加
for(int i = 0; i < 10; i++)
{
int newSize = ArraySize(prices) + 1;
ArrayResize(prices, newSize);
prices[newSize - 1] = Close[i];
}
Print("配列サイズ: ", ArraySize(prices));
Print("最初の要素: ", prices[0]);
Print("最後の要素: ", prices[ArraySize(prices) - 1]);
}
// 予約サイズを使った効率的な拡張
void EfficientResize()
{
double data[];
ArrayResize(data, 0, 1000); // 1000要素分のメモリを予約
// 追加時にメモリ再割り当てが発生しにくい
for(int i = 0; i < 500; i++)
{
ArrayResize(data, i + 1);
data[i] = MathRand();
}
}ArrayCopy — 配列コピー
int ArrayCopy(
void& dst_array[], // コピー先
void src_array[], // コピー元
int dst_start = 0, // コピー先の開始位置
int src_start = 0, // コピー元の開始位置
int count = WHOLE_ARRAY // コピーする要素数
);
// 戻り値: コピーした要素数void CopyExample()
{
double source[] = {1.0, 2.0, 3.0, 4.0, 5.0};
double dest[];
// 全要素コピー
ArrayResize(dest, ArraySize(source));
ArrayCopy(dest, source);
// 部分コピー(3番目から2要素)
double partial[];
ArrayResize(partial, 2);
ArrayCopy(partial, source, 0, 2, 2); // source[2], source[3]をコピー
// partial = {3.0, 4.0}
// 終値の直近20本をコピー
double recentClose[];
ArrayResize(recentClose, 20);
ArrayCopy(recentClose, Close, 0, 0, 20);
}ArraySort — ソート
bool ArraySort(
void& array[], // 対象配列
int count = WHOLE_ARRAY, // ソートする要素数
int start = 0, // 開始位置
int direction = MODE_ASCEND // MODE_ASCEND(昇順) / MODE_DESCEND(降順)
);void SortExample()
{
double values[] = {5.0, 2.0, 8.0, 1.0, 9.0, 3.0};
// 昇順ソート
ArraySort(values);
// values = {1.0, 2.0, 3.0, 5.0, 8.0, 9.0}
// 降順ソート
ArraySort(values, WHOLE_ARRAY, 0, MODE_DESCEND);
// values = {9.0, 8.0, 5.0, 3.0, 2.0, 1.0}
}
// 直近N本の高値・安値の中央値を計算
double MedianPrice(int bars)
{
double highs[];
ArrayResize(highs, bars);
for(int i = 0; i < bars; i++)
highs[i] = High[i + 1]; // 確定バーから
ArraySort(highs);
if(bars % 2 == 0)
return (highs[bars/2 - 1] + highs[bars/2]) / 2.0;
else
return highs[bars/2];
}ArrayMaximum / ArrayMinimum
int ArrayMaximum(
void array[], // 対象配列
int count = WHOLE_ARRAY, // 検索する要素数
int start = 0 // 開始位置
);
// 戻り値: 最大値のインデックス
int ArrayMinimum(
void array[],
int count = WHOLE_ARRAY,
int start = 0
);
// 戻り値: 最小値のインデックスvoid FindHighLow(int bars)
{
// 直近N本の最高値・最安値
int highIdx = iHighest(NULL, 0, MODE_HIGH, bars, 1);
int lowIdx = iLowest(NULL, 0, MODE_LOW, bars, 1);
Print("直近", bars, "本の最高値: ", High[highIdx], " (", highIdx, "本前)");
Print("直近", bars, "本の最安値: ", Low[lowIdx], " (", lowIdx, "本前)");
// 配列版
double myData[] = {10.5, 20.3, 5.8, 15.2, 30.1};
int maxIdx = ArrayMaximum(myData);
int minIdx = ArrayMinimum(myData);
Print("最大値: ", myData[maxIdx], " at index ", maxIdx);
Print("最小値: ", myData[minIdx], " at index ", minIdx);
}配列関数のArrayMaximum/ArrayMinimumとは別に、チャートの価格データを直接検索するiHighest() / iLowest()関数もあります。
int iHighest(string symbol, int timeframe, int type, int count, int start); int iLowest(string symbol, int timeframe, int type, int count, int start); // type: MODE_HIGH, MODE_LOW, MODE_OPEN, MODE_CLOSE, MODE_VOLUME
直近20本の最高値のバーインデックスを取得する場合: int idx = iHighest(NULL, 0, MODE_HIGH, 20, 1);
配列関数のArrayMaximum/ArrayMinimumとは別に、チャートの価格データを直接検索するiHighest() / iLowest()関数もあります。
int idx = iHighest(NULL, 0, MODE_HIGH, 20, 1); … 直近20本の最高値のバーインデックスを取得
ArrayInitialize — 配列の初期化
int ArrayInitialize(
double& array[], // 対象配列
double value // 初期値
);
// 全要素を指定値で初期化。戻り値: 初期化した要素数void InitExample()
{
double buffer[100];
// 全要素を0.0に初期化
ArrayInitialize(buffer, 0.0);
// 全要素をEMPTY_VALUE(空値)に初期化
ArrayInitialize(buffer, EMPTY_VALUE);
}ArraySetAsSeries — 時系列インデックス
bool ArraySetAsSeries(
void& array[], // 対象配列
bool flag // true=時系列(最新=0), false=通常(最古=0)
);void SeriesExample()
{
double data[];
ArrayResize(data, 5);
data[0] = 100; data[1] = 101; data[2] = 102; data[3] = 103; data[4] = 104;
// 通常: data[0]=100(最古), data[4]=104(最新)
Print("通常: [0]=", data[0], " [4]=", data[4]);
// 時系列に変更
ArraySetAsSeries(data, true);
// 時系列: data[0]=104(最新), data[4]=100(最古)
Print("時系列: [0]=", data[0], " [4]=", data[4]);
// Close[], High[]等は最初から時系列([0]=現在のバー)
Print("Close[0](現在)=", Close[0]);
Print("Close[1](1本前)=", Close[1]);
}- MQL4の定義済み配列(Close[], High[], Low[], Open[], Time[], Volume[])は最初から時系列([0]=現在のバー)
- 自分で作った配列にArraySetAsSeries(arr, true)を設定すると、インデックスの向きが反転する
- ArraySort()は時系列配列では正しくソートされない場合がある。ArraySetAsSeries(arr, false)にしてからソートする
- MQL5ではCopyBuffer()で取得した配列がデフォルトで時系列ではないため、移植時に注意
- MQL4の定義済み配列(Close[], High[], Low[], Open[], Time[], Volume[])は最初から時系列([0]=現在のバー)
- 自分で作った配列にArraySetAsSeries(arr, true)を設定すると、インデックスの向きが反転する
- ArraySort()は時系列配列では正しくソートされない場合がある。ArraySetAsSeries(arr, false)にしてからソートする
- MQL5ではCopyBuffer()で取得した配列がデフォルトで時系列ではないため、移植時に注意
その他の配列関数
| 関数 | 説明 |
|---|---|
| ArraySize(array) | 配列の全要素数 |
| ArrayRange(array, dimension) | 指定次元のサイズ |
| ArrayDimension(array) | 配列の次元数 |
| ArrayFree(array) | 動的配列のメモリ解放 |
| ArrayIsSeries(array) | 時系列配列かどうか |
| ArrayIsDynamic(array) | 動的配列かどうか |
| ArrayBsearch(array, value) | 二分探索(ソート済み配列用) |
配列関数一覧(MQL5対応表)
| MQL4関数 | MQL5対応 | 説明 |
|---|---|---|
| ArrayResize() | ArrayResize() | サイズ変更 |
| ArrayCopy() | ArrayCopy() | 配列コピー |
| ArraySort(arr, cnt, start, dir) | ArraySort(arr)(昇順のみ) | ソート |
| ArrayMaximum() | ArrayMaximum() | 最大値インデックス |
| ArrayMinimum() | ArrayMinimum() | 最小値インデックス |
| ArrayInitialize() | ArrayInitialize() | 全要素初期化 |
| ArraySetAsSeries() | ArraySetAsSeries() | 時系列設定 |
| ArraySize() | ArraySize() | 要素数取得 |
| ArrayRange() | ArrayRange() | 次元サイズ取得 |
| ArrayFree() | ArrayFree() | メモリ解放 |
| ArrayBsearch() | ArrayBsearch() | 二分探索 |
まとめ
MQL4の配列関数はMQL5とほぼ共通で、移植性が高いカテゴリです。重要なポイントは以下の通りです。
- 動的配列はArrayResize()でサイズ変更 — reserve_sizeを使うと頻繁なリサイズが効率化される
- Close[], High[]等は時系列配列 — [0]が最新バー、インデックスが増えると過去に遡る
- ArraySort()はMQL5では昇順のみ — MQL4のMODE_DESCENDはMQL5移植時に注意
- ArraySetAsSeries()で通常配列を時系列に変換できるが、インデックスの向きに注意
次のステップとして、MQLリファレンス総合ガイドで他のカテゴリも学習しましょう。





