OBV(オンバランスボリューム)は、株式投資の本やサイトで必ず紹介される、

定番の出来高分析指標です。

MT4の`iOBV()`をそのまま使って、

同じ意味で読み取ってよいのか迷ったことはないでしょうか。

実は、本来のOBVは「実際に売買された株数」という実出来高を前提にした指標です。

FXのMT4が提供するのは出来高そのものではなく、

「ティックボリューム(値段が動いた回数)」です。

この前提の違いを知らずに使うと、解釈を誤ります。

この記事では、OBVの本来の考え方と`iOBV()`の引数・戻り値を確認したうえで、

FXで使う場合に気をつけるべき点を解説します。

あわせて、折れ線だけでは判断しづらいOBVの弱点を補う、

「傾き矢印」付きインジケーターの実装コードも紹介します。

この記事で分かること
・OBVが前提にしている『実出来高』とは何か
・iOBV()の引数と戻り値の見方
・FXのティックボリュームでOBVを使う際の注意点
・OBVの『傾き』を矢印で知らせるインジケーターの作り方

OBV(オンバランスボリューム)とは何か

まず、`iOBV()`が計算している指標そのものの考え方を確認します。

上昇日に出来高を足し、下落日に出来高を引くという計算の仕組み

OBVは、価格が前の時点より上昇した日はその日の出来高を足し、

下落した日はその日の出来高を引く、という単純な積み上げで計算されます。

価格が変わらなければ、その日の出来高は加算しません。

この積み上げの線が上向きなら「買いの勢いが強い」、下向きなら「売りの勢いが強い」

と読みます。

本来のOBVは株式市場の「実出来高」を前提にした指標

OBVを考案したジョー・グランビルは、株式市場の「実際に成立した売買株数」

を前提にしていました。

出来高が価格の先行指標になる、という考え方が土台にあります。

FXのMT4ではティックボリュームを使うしかない(ここが最大の注意点)

注意
・FXは取引所を介さないため『実際の売買量』を把握できません
・MT4のVolume[]やiVolume()が返すのはティックボリュームです
・real_volume(実出来高)は多くのFXブローカーで0のままです

つまりFXで`iOBV()`を使うと、

内部的には「出来高」の代わりにティックボリュームが積み上げられます。

値動きの活発さの指標としてはそれなりに機能しますが、「実際の売買量の偏り」

という本来の意味までは保証されない、という前提を理解しておく必要があります。

iOBV関数のシグネチャと戻り値

次に、`iOBV()`の書式を確認します。

iOBV()の引数と戻り値の見方

double iOBV(
   string symbol,       //通貨ペア(NULLで現在の通貨ペア)
   int    timeframe,    //時間足(0で現在の時間足)
   int    applied_price,//計算に使う価格(PRICE_CLOSE等)
   int    shift          //何本前の値を取得するか(0が最新の確定前の値)
   );

戻り値はdouble型で、OBVの積み上げ値そのものを返します。

絶対値そのものには意味がなく、「前回の値より増えたか減ったか」

という変化の方向を見るのが基本です。

applied_priceは何を基準に上げ下げを判定するか

`applied_price`は、各バーが「上昇」か「下落」

かを判定する基準価格を指定します。

一般的には終値同士を比較する`PRICE_CLOSE`を指定するのが基本で、

他のオシレーター系関数と同じ`ENUM_APPLIED_PRICE`の、

定数がそのまま使えます。

OBVの折れ線だけでは判断しづらい理由と「傾き矢印」のアイデア

OBVは積み上げ式のため、そのままでは読み取りにくいという弱点があります。

OBVは価格と同じようにトレンドを描くため単独では使いにくい

OBVの折れ線は、価格チャートと同じようにずっと右肩上がり・右肩下がりの形になりがちです。

線の形だけを見ても「今が強いのか弱いのか」を一目で判断しにくい、という弱点があります。

直近の傾き(差分)を計算して矢印で知らせる設計にする

そこで、OBVの絶対値ではなく「直近N本の傾き(差分)」を計算し、

傾きが一定以上プラスなら上向き矢印、マイナスなら下向き矢印を表示する設計にします。

osma-cross-arrow-indicator.mdと同じ『状態でなく変化を検知する』考え方

これは既刊のOsMAゼロクロス矢印インジケーターと同じ考え方で、

「今の値そのもの」ではなく「変化が起きた瞬間」を矢印で可視化することで、

折れ線を目で追い続ける負担を減らします。

iOBVの傾きを矢印で表示するサンプルコード

傾き判定と矢印表示を組み込んだカスタムインジケーターです。

//+------------------------------------------------------------------+
//|                                             ObvSlopeArrow.mq4     |
//|                     Copyright 2026, FX-EA System Project Creator |
//|                        https://creator.fx-ea-system-project.com/ |
//+------------------------------------------------------------------+
#property strict
#property indicator_chart_window
#property indicator_buffers 2

double UpArrow[];
double DownArrow[];

input int    InpSlopeBars = 5;     //傾きを計算する本数
input double InpThreshold = 0.0;   //矢印を出す傾きのしきい値

int OnInit()
  {
   SetIndexBuffer(0, UpArrow);
   SetIndexStyle(0, DRAW_ARROW);
   SetIndexArrow(0, 233);

   SetIndexBuffer(1, DownArrow);
   SetIndexStyle(1, DRAW_ARROW);
   SetIndexArrow(1, 234);

   return(INIT_SUCCEEDED);
  }

int OnCalculate(const int rates_total,
                const int prev_calculated,
                const datetime &time[],
                const double &open[],
                const double &high[],
                const double &low[],
                const double &close[],
                const long &tick_volume[],
                const long &volume[],
                const int &spread[])
  {
   int start = (prev_calculated > InpSlopeBars) ? rates_total - prev_calculated : rates_total - InpSlopeBars - 2;
   if(start < 0)
      start = 0;

   for(int i = start; i < rates_total; i++)
     {
      int shift = rates_total - 1 - i;
      if(shift + InpSlopeBars > rates_total - 1)
         continue;

      double obvNow  = iOBV(_Symbol, 0, PRICE_CLOSE, shift);
      double obvPrev = iOBV(_Symbol, 0, PRICE_CLOSE, shift + InpSlopeBars);
      double slope = obvNow - obvPrev;

      UpArrow[i]   = EMPTY_VALUE;
      DownArrow[i] = EMPTY_VALUE;

      if(slope > InpThreshold)
         UpArrow[i] = low[i] - 10 * _Point;
      else if(slope < -InpThreshold)
         DownArrow[i] = high[i] + 10 * _Point;
     }

   return(rates_total);
  }

このコードは`OnCalculate()`の時系列配列を直接使い、

`iOBV()`で現在値と`InpSlopeBars`本前の値を比較して傾きを判定します。

MetaEditorでのコンパイル・表示手順

  1. MetaEditorで新規カスタムインジケーター「ObvSlopeArrow」を作成し、上のコードを貼り付けてコンパイルする
  2. チャートにドラッグ&ドロップで適用する
  3. 価格が一方向に動いた区間の直後に、ローソク足の上下に矢印が表示されることを確認する
  4. `InpSlopeBars`の値を変えて、矢印が出る頻度がどう変わるかを確認する

よくあるエラーと注意点

実際に使う前に確認しておきたい注意点をまとめます。

FXではOBVが「出来高の絶対値」として意味を持たない

補足
・FXのOBVは『ティックボリュームの積み上げ』であり、実際の資金の出入りではありません
・単独の売買判断材料にはせず、価格の勢いを補強する補助指標として使うのが安全です

ティックボリュームが0のまま進むヒストリカルデータでの誤動作

既刊のiVolume/CopyRates記事で解説した通り、

一部のヒストリカルデータでは出来高が0のまま記録されているバーが混ざっています。

OBVはこの区間で変化がないまま横ばいになるため、傾きがずっとゼロ付近になり矢印が出ない、

という現象が起きることがあります。

よくある質問

iOBVについて、よく検索される疑問に回答します。

OBVはFXでは全く使えないということですか?

使えないわけではありません。

ティックボリュームでも「値動きが活発な時間帯」を知る手がかりにはなります。

ただし、本来の『実際の売買量の偏り』という株式市場的な意味までは保証されない、

という前提で使う必要があります。

傾きのしきい値(InpThreshold)はどう決めればよいですか?

通貨ペアや時間足によって出来高の桁数が大きく変わるため、まずは`0`のまま動かしてみて、

矢印の出現頻度が多すぎる場合に少しずつ上げていくのがおすすめです。

MQL5でもiOBVは使えますか?

MQL5には`iOBV()`という単体関数はなく、

`iOBV()`相当の処理はハンドルを作成して、

`CopyBuffer()`で値を取得する方式に変わります。

既刊のCopyBuffer/CopyRates記事と同じ『ハンドル方式』

の考え方がそのまま当てはまります。

【MQL4】iOBV(オンバランスボリューム)の使い方を解説してみた(FXのティックボリュームで本来の意味は通用するか):まとめ

OBVは株式市場の『実出来高』を前提にした指標であり、

FXのMT4で使う場合は『ティックボリューム』

という別の前提に置き換わっていることを理解しておく必要があります。

折れ線の絶対値ではなく、直近の傾きを矢印で可視化することで、

OBVを補助的な勢いの確認材料として扱いやすくなります。

関連記事