Problem Description
Solution
To split a string into multiple parts in MQL4, you use the StringSplit() function. This function takes a source string, a separator character (converted to ASCII code), and a dynamic string array where the resulting substrings will be stored.
Here is a complete, runnable script that demonstrates how to split a comma-separated string. I have included a practical use case: parsing a "signal string" that might be received from an external source (like a CSV file or web request) containing trade parameters.
MQL4 Script: String Splitting and Processing
//+------------------------------------------------------------------+
//| StringSplitExample.mq4 |
//| Copyright 2023, MetaQuotes Software Corp. |
//| https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2023, MetaQuotes Software Corp."
#property link "https://www.mql5.com"
#property version "1.00"
#property strict
#property script_show_inputs
//--- Input parameters
input string InpSignalString = "EURUSD,OP_BUY,0.1,1.0850,1.0950"; // Format: Symbol,Type,Lots,SL,TP
input string InpSeparator = ","; // Separator character
//+------------------------------------------------------------------+
//| Script program start function |
//+------------------------------------------------------------------+
void OnStart()
{
// 1. Prepare the separator
// StringSplit requires the separator to be a ushort (ASCII code).
// We get the code of the first character of the input separator string.
ushort u_sep = StringGetCharacter(InpSeparator, 0);
// 2. Prepare the array to store results
string result_array[];
// 3. Execute the split
// The function returns the number of substrings found.
// The 'result_array' is passed by reference and populated automatically.
int substring_count = StringSplit(InpSignalString, u_sep, result_array);
// 4. Validate results
if(substring_count > 0)
{
Print("Successfully split string into ", substring_count, " parts.");
// 5. Process each part
// We loop through the array to process the data.
for(int i = 0; i < substring_count; i++)
{
// It is good practice to trim whitespace in case the string was "A, B, C"
string current_part = result_array[i];
StringTrimLeft(current_part);
StringTrimRight(current_part);
PrintFormat("Part [%d]: %s", i, current_part);
}
// 6. Practical Application: Parsing the specific signal format
// Expected format: Symbol, Operation, Lots, SL, TP
if(substring_count == 5)
{
ProcessTradeSignal(result_array);
}
else
{
Print("Error: Input string does not match expected format (5 parameters).");
}
}
else
{
Print("Error: No substrings found or empty input.");
}
}
//+------------------------------------------------------------------+
//| Helper function to interpret the split data |
//+------------------------------------------------------------------+
void ProcessTradeSignal(string& args[])
{
Print("--- Processing Trade Signal ---");
// Index 0: Symbol
string symbol = args[0];
// Index 1: Operation Type (String to Enum conversion logic)
string op_string = args[1];
int cmd = -1;
if(StringFind(op_string, "BUY") >= 0) cmd = OP_BUY;
else if(StringFind(op_string, "SELL") >= 0) cmd = OP_SELL;
// Index 2: Volume (String to Double)
double volume = StringToDouble(args[2]);
// Index 3: Stop Loss (String to Double)
double sl = StringToDouble(args[3]);
// Index 4: Take Profit (String to Double)
double tp = StringToDouble(args[4]);
// Output the parsed logic
if(cmd != -1)
{
PrintFormat("Signal Detected: %s %s Volume: %.2f SL: %.5f TP: %.5f",
symbol, op_string, volume, sl, tp);
// Logic to execute trade would go here:
// OrderSend(symbol, cmd, volume, price, slippage, sl, tp, ...);
}
else
{
Print("Error: Unknown operation type in signal.");
}
}
//+------------------------------------------------------------------+
Key Functions Used
StringGetCharacter(string, pos):StringSplitrequires the separator to be of typeushort(the ASCII code), not astring. This function extracts the code from your separator string (e.g., extracting code 44 from ",").StringSplit(string, separator, array[]): This is the core function. It resizes the dynamic arrayresult_arrayautomatically and fills it with the substrings. It returns the count of elements found.StringTrimLeft()/StringTrimRight(): When parsing CSVs or user input, spaces often creep in (e.g.,"EURUSD, OP_BUY"). Trimming ensures conversion functions likeStringToDoublework correctly.StringToDouble()/StringToInteger(): Used to convert the parsed string parts into numerical values required for trading functions likeOrderSend.
Common Pitfalls
- Array Sizing: You do not need to manually
ArrayResizethe destination array before callingStringSplit. The function handles memory allocation for you. - Separator Type: Passing a string literal
","directly as the second argument toStringSplitwill cause a compilation error. You must pass theushortcharacter code (e.g.,','or(ushort)44).
Q&A: String Manipulation in MQL4
Q: Can I use a multi-character separator (like ";;") with StringSplit?
A: No, StringSplit only accepts a single character (ushort) as a separator. If you need to split by a multi-character delimiter, you must write a custom function using StringFind and StringSubstr.
Q: What happens if the string starts with the separator?
A: The first element of the resulting array will be an empty string "".
Q: How do I handle CSV lines that might contain text with commas inside quotes?
A: The standard StringSplit function is naive; it splits on every occurrence of the separator. It does not respect quotes (e.g., "Comment, with comma", 1.0). For complex CSV parsing involving quotes, you must implement a custom parser that iterates through the string character by character.
Q: Is there a limit to the number of substrings?
A: The limit is dictated by available memory, but practically, StringSplit is very efficient for standard data processing tasks in trading.