//+------------------------------------------------------------------+
//| Expert initialization function |
//+------------------------------------------------------------------+
input int EMA1_Period = 9; // First EMA period
input int EMA2_Period = 20; // Second EMA period
input double RiskPercent = 1.0; // Risk percentage per trade
input double TakeProfitFactor = 1.5; // Take Profit as a factor of SL
input double StopLossPips = 50; // Stop Loss in pips
input int MartingaleStep = 2; // Martingale multiplier
input int MaxMartingaleSteps = 3; // Maximum martingale steps
double Lots; // Trade lots
//+------------------------------------------------------------------+
//| Expert tick function |
//+------------------------------------------------------------------+
void OnTick()
{
double ema1 = iMA(Symbol(), 0, EMA1_Period, 0, MODE_EMA, PRICE_CLOSE, 0);
double ema2 = iMA(Symbol(), 0, EMA2_Period, 0, MODE_EMA, PRICE_CLOSE, 0);
// Get the latest bid/ask prices
double bid = NormalizeDouble(SymbolInfoDouble(Symbol(), SYMBOL_BID), _Digits);
double ask = NormalizeDouble(SymbolInfoDouble(Symbol(), SYMBOL_ASK), _Digits);
// Check if there are open positions
if (PositionsTotal() == 0)
{
// If EMA1 is above EMA2, it's a buy signal
if (ema1 > ema2)
{
OpenTrade(ORDER_TYPE_BUY, ask);
}
// If EMA1 is below EMA2, it's a sell signal
else if (ema1 < ema2)
{
OpenTrade(ORDER_TYPE_SELL, bid);
}
}
else
{
// Implement martingale if there's a loss
ManageMartingale();
}
}
//+------------------------------------------------------------------+
//| Open trade function |
//+------------------------------------------------------------------+
void OpenTrade(int orderType, double price)
{
double sl = 0, tp = 0;
Lots = CalculateLots(); // Calculate the lot size based on risk percentage
// Set stop loss and take profit
if (orderType == ORDER_TYPE_BUY)
{
sl = NormalizeDouble(price - StopLossPips * _Point, _Digits);
tp = NormalizeDouble(price + StopLossPips * TakeProfitFactor * _Point, _Digits);
}
else if (orderType == ORDER_TYPE_SELL)
{
sl = NormalizeDouble(price + StopLossPips * _Point, _Digits);
tp = NormalizeDouble(price - StopLossPips * TakeProfitFactor * _Point, _Digits);
}
// Create the trade request structure
MqlTradeRequest request;
MqlTradeResult result;
ZeroMemory(request);
request.action = TRADE_ACTION_DEAL;
request.symbol = Symbol();
request.volume = Lots;
request.type = orderType;
request.price = price;
request.sl = sl;
request.tp = tp;
request.deviation = 10;
request.magic = 123456;
request.comment = "EMA Crossover EA";
// Send the trade order
OrderSend(request, result);
}
//+------------------------------------------------------------------+
//| Manage martingale positions |
//+------------------------------------------------------------------+
void ManageMartingale()
{
for (int i = PositionsTotal() - 1; i >= 0; i--)
{
if (PositionSelect(Symbol())) // Select position by symbol
{
double posPrice = PositionGetDouble(POSITION_PRICE_OPEN);
double currentPrice = PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_BUY ? SymbolInfoDouble(Symbol(), SYMBOL_BID) : SymbolInfoDouble(Symbol(), SYMBOL_ASK);
double loss = PositionGetDouble(POSITION_PROFIT);
// If the position is in loss and within martingale steps
if (loss < 0 && PositionGetInteger(POSITION_TICKET) <= MaxMartingaleSteps)
{
// Double the lot size for the next position
Lots *= MartingaleStep;
// Open the same position type but with a higher lot size
if (PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_BUY)
OpenTrade(ORDER_TYPE_BUY, SymbolInfoDouble(Symbol(), SYMBOL_ASK));
else
OpenTrade(ORDER_TYPE_SELL, SymbolInfoDouble(Symbol(), SYMBOL_BID));
}
}
}
}
//+------------------------------------------------------------------+
//| Calculate lot size based on risk percentage |
//+------------------------------------------------------------------+
double CalculateLots()
{
double riskAmount = AccountInfoDouble(ACCOUNT_BALANCE) * (RiskPercent / 100); // Fixed AccountInfoDouble
double stopLossValue = StopLossPips * SymbolInfoDouble(Symbol(), SYMBOL_TRADE_TICK_VALUE);
return NormalizeDouble(riskAmount / stopLossValue, 2);
}
我尝试在 chatgpt 的帮助下编写基于 ema 9 和 ema 20 交叉的 ea,但它向我展示了这个问题: 'iMA' - 错误参数计数 emadx.mq5 19 18 内置:int iMA(const string,ENUM_TIMEFRAMES,int,int,ENUM_MA_METHOD,int) emadx.mq5 19 18 'iMA' - 错误参数计数 emadx.mq5 20 18 内置: int iMA(const string,ENUM_TIMEFRAMES,int,int,ENUM_MA_METHOD,int) emadx.mq5 20 18
有人可以帮助我吗?
看来您提供了太多的一个参数。
int iMA(
string symbol, // symbol name
ENUM_TIMEFRAMES period, // period
int ma_period, // averaging period
int ma_shift, // horizontal shift
ENUM_MA_METHOD ma_method, // smoothing type
ENUM_APPLIED_PRICE applied_price // type of price or handle
);
这是 MetaTrader 5 文档中对
iMA()
函数的官方参考,其中解释了该函数以及所有必需参数的正确用法: