English Русский 中文 Español 日本語 Português 한국어 Français Italiano Türkçe
Die Grundlagen von MQL5 Strings

Die Grundlagen von MQL5 Strings

MetaTrader 5Beispiele | 27 Juni 2016, 16:29
3 031 0
Dmitry Fedoseev
Dmitry Fedoseev

Einleitung

Strings, oder String Variablen, werden verwendet, um Zeichendaten zu speichern, zum Beispiel Text.

string str="Any text";

Die Sprache MQL5 bietet ein breites Spektrum benutzerfreundlicher Funktionen für Operationen mit Strings. Beim Programmieren von Expert Advisors und Indikatoren werden Strings meistens für die Generierung von Informationsnachrichten verwendet. Bei Indikatoren sind dies meist Nachrichten über die Erfüllung bestimmter Konditionen (z.B. Handelssignale), während sie bei Expert Advisors Handelsaktivitätsergebnisse berichten. Während er läuft, kann ein Expert Advisor, Skript oder Indikator Parameter kontrollieren, die vom Benutzer bestimmt werden und eine Benachrichtigung ausdrucken wenn die gesetzten Parameter ungültig sind. Zusätzlich zu den Benachrichtigungen können Sie manchmal Benutzerführungsnachrichten sehen, die Empfehlungen über Parametereinstellungen geben. Beim Programmieren in MQL5 bieten Strings also vor allem Benutzerfreundlichkeit.

Außerdem sind Strings unabdingbar beim Arbeiten mit Dateien. Mit String-Variablen kann man auf Dateien schreiben und sie lesen. Natürlich kann man sich auch für eine andere Art entscheiden, um mit Dateien zu arbeiten, eine binäre Methode, mit der man numerische Variablen und Arrays lesen und schreiben kann. Wenn die Menge an Daten jedoch nicht zu groß ist, ist es besser, Textdateien und Strings zu verwenden. In diesem Fall ist die Programmbedienung für den Benutzer klarer und der Prozess der Programmentwicklung ist einfacher, da er eine unmittelbare Datenkontrolle bietet. Textdateidaten schauen gleich aus wie Daten in dem Programm.

Die Benutzung von Strings kann die Programmeigenschaften, die mit Daten (Parameter) Input assoziiert werden, signifikant erweitern wenn die benötigte Anzahl von Parametern im Vorhinein nicht feststeht (z.B. Los-Größen für durchschnittliche Anhäufungen). In so einem Fall werden die Werte auf einen einzelnen String geschrieben, der von einem Separator getrennt wird, zum Beispiel einem Strichpunkt.

input string Lots="0.1; 0.2; 0.3; 0.5";

Dann, wenn der Expert Advisor initialisiert wird, ist der String gespalten und ein Array von numerischen Werten wird ausgefüllt. Leider ist es unmöglich, im Optimierungsprozess über solche String-Parameter zu gehen, das heißt, den Anfangs- und Endwert zusammen mit dem Schrittwert zu bestimmen. In solchen Fällen ist es vielleicht besser, eine große Anzahl an numerischen Variablen im Eigenschaftsfenster zu verwenden. Aber da diese eine unendliche Anzahl haben können, haben wir vielleicht einen Fall von Bequemlichkeit und Zweck vor uns (wenn die Möglichkeit der Optimierung erforderlich ist).

Vielleicht gibt es auch andere Fälle, in denen die Optimierung von Parametern nicht erforderlich ist, zum Beispiel die Aktivierung von Benachrichtigungen. MQL5 unterstützt verschiedene Methoden der Benutzerbenachrichtigung: Benachrichtigungen mit Ton, Pop-up-Fenster, E-mail-Benachrichtigungen und Push-Benachrichtigungen. Für jede dieser Benachrichtigungen können im Fenster "Eigenschaften" Bool-Schalter eingerichtet werden, wofür man mindestens vier Variablen braucht. Man kann aber auch die Anzahl der Variablen auf eine String-Variable reduzieren.

Wenn Sie den Ton bei Benachrichtigungen aktivieren wollen, schreiben Sie "s" (sound). Wenn Sie auch E-mail-Benachrichtigungen bekommen wollen, fügen Sie "e" hinzu. So kann man jegliche Kombination von Benachrichtigungen mit nur einer Variable aktivieren. Für einen Expert Advisor ist die Anzahl externer Parameter von geringer Bedeutung. Es geht nur um Benutzerfreundlichkeit.

Andererseits sollte man bei der Entwicklung von Indikatoren auf eine Reduzierung der Anzahl externer Parameter achten. Es ist sehr wahrscheinlich, dass der Indikator von einem Expert Advisor oder einem anderen Indikator mit den Funktionen iCustom() oder IndicatorCreate() aufgerufen wird, deren Anzahl an Parametern limitiert ist (iCustom() hat nur 64 Parameter und die Parameter-Array-Größe der Funktion IndicatorCreate() beträgt 64 Elemente). Die Verwendung von Strings könnte demzufolge von großem praktischen Nutzen sein.

In diesem Artikel werden alle Standardfunktionen von MQL5, die sich mit der Arbeit mit Strings befassen, evaluiert, und wir werden auch ein paar nützliche, benutzerdefinierte Funktionen erstellen.

 

Wie man eine String-Variable deklariert

Wie jede andere Form von Variablen können String-Variablen deklariert werden:

string str;
oder es wird ihnen nach der Deklarierung Wert zugeteilt (mit einem Wert initialisiert):
string str="Any text";

Es bestehen keinerlei Einschränkungen die String-Länge betreffend. Ein langer String kann der Einfachheit halber in mehrere Teil-Strings aufgeteilt werden:

string str= "A long string can be "
            "split into several "
            "substrings";
//--- output the results
Alert(str);

Bei einer solchen Initialisierung wird die String-Variable die Information enthalten: "Ein langer String kann in mehrere Teil-Strings geteilt werden."

Hier sollten wir beachten, dass der Wert einer String-Variable ohne Parameter nicht gleich einem leeren String ist:

string str="";

Sie können es selbst sehen:

string str1;
string str2="";
//--- output the comparison results
Alert(str1==str2);

Wenn dieser Code läuft, wird ein Fenster mit dem Alarmsignal "falsch" erscheinen. Eine String-Variable, die nicht initialisiert wurde, hat den Wert NULL, der nicht das gleiche ist wie ein leerer String "". Das sollten Sie auf jeden Fall beachten! Bei der Arbeit mit Strings müssen wir oft überprüfen, ob ein String leer ist. Daher sollten Sie sich entweder an die Regeln halten und alle Strings mit einem leeren String "" initialisieren, oder überprüfen, dass sie nicht gleich "" sind und nicht gleich NULL:

if(str!="" && str!=NULL)
  {
   //--- some operation with a string
  }

Die erste Methode ist mehr zu empfehlen, da sie die Überprüfungsbedingungen vereinfacht.  

Sie können das gleiche tun, indem Sie die Größe einer Variable überprüfen. Um die Größe zu bestimmen, verwenden wir die Funktion StringLen().

if(StringLen(str)!=0)
  { 
   //--- some operation with a string
  }


Wie man Strings verkettet

Der Vorgang, der bei der Arbeit mit Strings am häufigsten ausgeführt wird, ist ihre Verkettung, das heißt, Phrasen mit Wörtern bauen. Verkettung wird durch das "+"-Zeichen implementiert:

string str1,str2,str3,str4,str5;
//--- assign values
str1="Programming";
str2="in MQL5";
str3="for MetaTrader 5";
//--- add up the strings
str4=str1+" "+str2;
str5=str1+" "+str3;
//--- output the results
Alert(str4);
Alert(str5);

Nach der Ausführung dieses Codes wird die str4-Variable "Programmieren in MQL5" enthalten, und die str5-Variable "Programmieren für MetaTrader 5". Das obige Beispiel zeigt, wie man zwei Strings verkettet, mit dem Ergebnis, dass der String einer anderen Variable zugeordnet wird.

Ein zusätzlicher String ist sehr oft mit dem Haupt-String verkettet:  

string str1,str2,str3;
//--- assign values
str1="Programming";
str2="in MQL5";
str3="for MetaTrader 5";
//--- add up the strings to the main string
str1=str1+" "+str2;
str1=str1+" "+str3;
//--- output the results
Alert(str1);

Nach der Ausführung dieses Codes wird der str1-String "Programmieren in MQL5 für MetaTrader 5" enthalten. Die obigen Beispiele zeigen, wie man Strings mit dem Haupt-String str1 verknüpfen kann und das Ergebnis letzterem zugeteilt wird. Die selben Vorgänge können auch viel einfacher geschrieben werden:

str1+=str2;
str1+=str3;
oder:
str1+=str2+str3;

Das Pluszeichen links vom Ist-Gleich-Zeichen bedeutet, dass das Zeichen rechts vom Ist-Gleich-Zeichen an die Variable str1 angehängt wird.

Sie können auch einen String an den Anfang des Hauptstrings anfügen. Diese Implementierung wird im zweitletzten Beispiel gezeigt: der Hauptstring wird zum zusätzlichen String hinzugefügt und der resultierende String wird der Hauptvariable zugeteilt.

string str1,str2,str3;
//--- assign values
str1="Programming";
str2="in MQL5";
str3="for MetaTrader 5";
//--- concatenate strings, with a string being added to the beginning
str3=str2+" "+str3;
str3=str1+" "+str3;
//--- output the results
Alert(str3);

Die folgende Phrase: "Programmieren in MQL5 für MetaTrader 5" wird nun in der Variable str3 sein. Sie können das gleiche mit einem einzelnen String implementieren:  

str3=str1+" "+str2+" "+str3;
In einigen Fällen kann man die Verkettung mit "," Komma ausführen. Das ist mit den Funktionen Alert(), Print() oder Comment() möglich:
Print(str1," ",str2," ",str3);

Das Endergebnis wird in diesem Fall identisch mit der Verwendung des Pluszeichens sein:

Print(str1+" "+str2+" "+str3);

Das Komma-Zeichen an sich verkettet keine Strings. Ein Komma ist ein Separator von Parametern in allen Funktionen. Das trifft auch auf die Funktionen Alert(), Print() und Comment() zu. Diese Funktionen haben einen verbindlichen Parameter und viele optionale. Parameter werden zur Funktion gegeben wo sie dann verkettet werden. Die Maximalanzahl ist 64.

Wir sehen etwas Ähnliches, wenn wir mit der Funktion FileWrite() einen String in eine Datei schreiben. Wenn Sie aber eine Datei im Modus FILE_CSV (mit Feld-Separatoren) öffnen, werden Kommas ersetzt durch Separator-Zeichen, wenn eine Datei geöffnet wird (wenn der Separator nicht angegeben ist, werden standardmäßig Tabulatoren verwendet). Wenn man im Modus FILE_TXT eine Datei öffnet, ohne den Separator festzulegen, werden die Ergebnisse bei Pluszeichen und Kommazeichen die gleichen sein.

//--- write to the first file
int h=FileOpen("1.txt",FILE_WRITE|FILE_ANSI|FILE_CSV);
FileWrite(h,"1","2","3");
FileClose(h);
//--- write to the second file
h=FileOpen("2.txt",FILE_WRITE|FILE_ANSI|FILE_CSV);
FileWrite(h,"1"+"2"+"3");
FileClose(h);
//--- write to the third file
h=FileOpen("3.txt",FILE_WRITE|FILE_ANSI|FILE_TXT);
FileWrite(h,"1","2","3");
FileClose(h);
//--- write to the fourth file
h=FileOpen("4.txt",FILE_WRITE|FILE_ANSI|FILE_TXT);
FileWrite(h,"1"+"2"+"3");
FileClose(h);

Nach der Ausführung dieses Codes wird die Datei 1.txt "1    2    3" enthalten, während die Datei 2.txt "123" enthalten wird (Dateien wurden im Modus FILE_CSV geöffnet). 3.txt und 4.txt werden identischen Inhalt haben: "123" (wird im Modus FILE_TXT geöffnet). Dieser Artikel behandelt keine Datei-Vorgänge. Wenn Ihnen also etwas in diesem Beispiel unklar ist, sorgen Sie sich nicht, es wird Ihr Verständnis der kommenden Abläufe nicht beeinträchtigen. Beachten Sie nur, dass die Verwendung des Plus- oder Kommazeichens nicht immer den selben Effekt hat, wenn man Strings erweitert.

Zusätzlich zum Pluszeichen bietet MQL5 auch spezielle Funktionen für das Hinzufügen von Strings: StringAdd() und StringConcatenate(). Laut der Beschreibung dieser Funktionen im Nachschlagewerk MQL5 können wir mit ihnen schneller und platzsparender Strings zusammenfügen (was den benötigten Arbeitsspeicher betrifft). Mit der Funktion StringAdd() können wir Strings zusammenfügen:

string str1,str2,str3;
//--- assign values
str1="Programming";
str2="in MQL5";
str3="for MetaTrader 5";
//--- call the function to concatenate strings
StringAdd(str1," ");
StringAdd(str1,str2);
StringAdd(str1," ");
StringAdd(str1,str3);
//--- output the results
Alert(str1);

Nach der Ausführung dieses Codes wird die str1-Variable "Programmieren in MQL5 für metaTrader 5" enthalten.

Mit der Funktion StringConcatenate() kann man gleichzeitig mehrere Strings kombinieren. Der erste Parameter, der in diese Funktion gegeben wird, ist die Variable des Strings zu dem weitere aufgelistete Strings angefügt werden können. Die Maximalanzahl an Parametern, die man in die Funktion geben kann, ist 64.

string str1,str2,str3;
//--- assign values
str1="Programming";
str2="in MQL5";

str3="for MetaTrader 5";
//--- call the function for combining several strings
StringConcatenate(str1,str1," ",str2," ",str3);
//--- output the results
Alert(str1);

Nach der Ausführung dieses Codes wird die str1-Variable auch "Programmieren in MQL5 für MetaTrader 5" enthalten.

 

Verschiedene Variablen in einen String konvertieren

Bei der Generierung eines Nachrichten-Strings müssen wir sehr oft Werte von numerischen Variablen hinzufügen. Um Werte von ganzzahligen Variablen (char, uchar, bool, short, ushort, int, uint, color, long, ulong, datetime) in einen String zu konvertieren, verwenden wir die Funktion IntegerToString():

int x=1;
string str="x = "+IntegerToString(x);

Bei der Konvertierung einer Bool-Variable wird ein retournierter String entweder '0' (falsch) oder '1' (richtig) enthalten. Wenn Farb- oder Zeitpunkt-Variablen konvertiert werden, wird ein retournierter String die numerische Formulierung von Farbe oder Zeitpunkt (zum Beispiel '6553' für Gelb clrYellow oder '1325376000' für folgendes Datum enthalten: 2012,01,01 00:00)

Um echte Variablen (double, float) in einen String zu konvertieren, verwenden wir die Funktion DoubleToString(). Der zweite Parameter dieser Funktion bestimmt die Präzisierung (die Anzahl an Dezimalzahlen):

double x=1.23456;
string str1="x = "+DoubleToString(x,2);
string str2="x = "+DoubleToString(x,3);

Nach der Ausführung dieses Codes wird die str1-Variable den String '1.23' enthalten, und die str2-Variable den String '1.235'. Mit mathematischen Rundungsregeln werden die Ziffern auf die festgelegte Anzahl verkürzt.

Die Funktion TimeToString() wird verwendet, um Datum und Zeit in einen standardformatigen String zu konvertieren (der von Menschen gelesen werden kann):

datetime tm=TimeCurrent(); // Current time 
string str1=IntegerToString(tm);
string str2=TimeToString(tm);

Nach der Ausführung dieses Codes wird die Variable str1 den String mit numerischen Formulierungen von Zeit enthalten (Sekunden, die vergangen sind seit 1. Januar 1970), während die Variable str2 die formatierte Zeit enthält, zum Beispiel "2012.11.02 22:00" (Jahr, Monat, Tag, Stunde, Minute).

Beim Ausführen der Funktion TimeToString() haben Sie die Option, das Datums- und Zeitformat festzulegen. Zur Auswahl stehen:

string str1="Date and time with minutes: "+TimeToString(tm);
string str2="Date only: "+TimeToString(tm,TIME_DATE);
string str3="Time with minutes only: "+TimeToString(tm,TIME_MINUTES);
string str4="Time with seconds only: "+TimeToString(tm,TIME_SECONDS);
string str5="Date and time with seconds: "+TimeToString(tm,TIME_DATE|TIME_SECONDS);

MQL5 bietet ein praktisches Feature um Aufzählungen zu erstellen, die in dem Fenster "Programmeigenschaften" als Drop-Down-Menü dargestellt werden. Werte solcher Variablen können mit der Funktion auch in einen String konvertiert werden EnumToString(). Unten ist der Skript-Code, der die Vorgänge dieser Funktion beschreibt:

//+------------------------------------------------------------------+
//| Create an enumeration                                            |
//+------------------------------------------------------------------+
enum EMode
  {
   OFF=0,
   Mode1 = 1,
   Mode2 = 2,
   Mode3 = 3 
  };
//+------------------------------------------------------------------+
//| Start the script                                                 |
//+------------------------------------------------------------------+
void OnStart()
  {
   EMode Value=1;
   //--- join strings together
   string str="The "+IntegerToString(Value)+ value" corresponds to "+EnumToString(Value)+ entry" of the Emode enumeration";
   //--- output the results
   Alert(str);
  } 
Es gibt eine ähnliche Möglichkeit, Farbvariablen zu konvertieren. Sie können mit der Funktion ColorToString() den Farbwert zum Namen der Farbe konvertieren:
color ColorValue=clrRed;
string str=ColorToString(ColorValue,true);

Nach der Ausführung dieses Codes wird die Variable str den String mit "clrRed" speichern. Wenn der zweite Parameter auf "falsch" eingestellt ist, wird die Funktion den String mit den Werten der RGB-Komponenten zurückgeben (Rot, Grün und Blau).

color ColorValue=clrRed;
string str=ColorToString(ColorValue,false);

In diesem Fall wird der in der Variable str gespeicherte String '255,0,0' sein. Sollte die gewünschte Farbe keine Standardfarbe sein (nicht auf der Web-Farbpalette definiert und daher namenlos), kann die Funktion ColorToString() verwendet werden, um den String mit Werten der Komponenten zu retournieren, ohne den zweiten Parameterwert zu berücksichtigen.

Man kann Variablen auch mit type casting konvertieren:

int x=123;
string str=(string)x;

Wenn eine boolesche Variable so konvertiert wird, ist der Stringwert entweder "richtig" oder "falsch".  

bool x=true;
string str=(string)x;

Das Konvertieren von double- und float-Variablen sollte so präzise wie möglich sein. Es erlaubt lediglich, Nullen im Bruchteil zu vernachlässigen:  

double x1=0.1;
double x2=0.123string str1=(string)x1;
string str2=(string)x2;

Nach der Ausführung dieses Codes wird die str1-Variable den Stringwert '0.1' speichern und die str2-Variable wird den Stringwert '0.123' enthalten.

 

Spezialzeichen-Ausgabe

Bei der Initialisierung einer String-Variable zu einem Wert sollte der zuzuteilende Wert in doppelten Anführungszeichen geschrieben werden, damit der Compiler den String vom Programm-Code unterscheiden kann. Um die Anführungszeichen in den String zu setzen, müssen Sie ausdrücklich klarmachen, dass die Anführungszeichen hier nicht verwendet werden, um ihren normalen Zweck zu erfüllen (als Zeichen, die einen String von einem Code unterscheiden), sondern Teil des Strings sind. Um dies zu implementieren, setzen Sie einen backslash "\" vor die Anführungszeichen:

string str1="Simple text";
string str2="\"Text in quotes\"";
//--- output the results
Alert(str1);
Alert(str2);

Da ein Backslash auch als Spezialzeichen gilt, sollte ein anderer Backslash vor ihn gesetzt werden, um die Ausgabe des Backslashes in einem String zu implementieren:

string str="\\";
Alert(str);

Nach der Ausführung dieses Codes ist das einzige Zeichen, das der String enthält, der Backslash ''\".

Ein String kann auch das horizontale Tabulator-Zeichen enthalten, vertreten mit '"\t":

string str="Column-1\tColumn-2\tColumn-3";
Alert(str);

In diesem Fall enthält die String-Variable den String "Column-1        Column-2        Column-3".

Ein Text kann auch mit Zeilenumbrüchen gedruckt werden, indem er mit dem Befehl "\n" auf verschiedene Zeilen geschrieben wird.

string str="Line-1\nLine-2\nLine-3";
Alert(str);

Als Ergebnis der Funktion Alert() werden Sie drei Zeilen Text haben.

Beim Drucken mit den Funktionen Alert() und MessageBox(), genauso wie beim Schreiben auf eine Datei, kann man sowohl "\t" und "\n" verwenden. Aber bei einem Diagrammkommentar (die Funktion Comment()) gilt nur "\n" als umhüllendes Zeichen, während das Zeichen "\t" ignoriert wird. Wenn die Ausgabe mit der Funktion Print() eingeleitet wird, kann man "\n" verwenden (jeder Teil eines Strings ist eine Ausgabe in einer anderen Zeile des Berichts) und "\t" wird ersetzt durch ein Leerzeichen wie in der Protokoll-Datei, die alle Nachrichtenausgaben mit der Funktion Print() speichert.

 

Modellbasiertes Formatieren von Strings

Beim Formatieren eines Strings für die Ausgabe müssen vielleicht Werte verschiedener numerischer Variablen inkludiert werden. Das macht man, indem man Strings zusammenfügt und numerische Variablen in Strings umwandelt. In diesem Fall ist der String eines Codes, der eine Nachricht baut, zu lang und zu schwer zu verstehen und bearbeiten, falls Bearbeitungen des Programms nötig werden sollten:

//--- initialize the variables
int Variable1=1;
int Variable2=2;
int Variable3=3;
//--- long addition of strings
string str="Variable1 = "+IntegerToString(Variable1)+", Variable2 = "+IntegerToString(Variable2)+", Variable3 = "+IntegerToString(Variable2);
//--- output the results
Alert(str);

Die gleiche Aufgabe kann viel leichter gelöst werden mit der Funktion StringFormat(). Der erste Parameter der in diese Funktion gegeben wird ist eine Nachrichtenvorlage, mit gekennzeichneten Plätzen um Variablen einzutragen und das Ausgabeformat festzulegen. Er wird gefolgt von Aufzählungen aller Variablen in der Reihenfolge wie sie in der Vorlage erscheinen:  

//--- initialize the variables
int Variable1=1;
int Variable2=2;
int Variable3=3;
//--- simpler addition of strings
string str=StringFormat("Variable1 = %i, Variable2 = %i, Variable3 = %i",Variable1,Variable2,Variable3);
//--- output the results
Alert(str);

Die Plätze für die Eingabe von Variablen sind mit "%" gekennzeichnet, gefolgt von "i", das im obigen Beispiel angibt, dass die Variablen als ganze Zahlen ausgegeben werden müssen. Anders gesagt steht"i" für ganze Zahlen (char, short, int, color) während "u" für vorzeichenlose, ganzzahlige Variablen verwendet wird (uchar, bool, ushort, uint). Für Variablen des Typus long, ulong und datetime sollten Sie zusätzlich die Größe der Variablen festlegen, indem Sie "I64" vor den Typus setzen:

string LongMin=StringFormat("%I64i",LONG_MIN);
string LongMax=StringFormat("%I64i",LONG_MAX);
string ULongMax=StringFormat("%I64u",ULONG_MAX);
string DateTimeMax=StringFormat("%I64u",DateMax);
//--- output the results
Alert("LongMin = "+LongMin);
Alert("LongMax = "+LongMax);
Alert("ULongMax = "+ULongMax);
Alert("DateTimeMax = "+DateTimeMax);
Als Ergebnis dieses Codes werden Sie ein Pop-Up-Fenster mit Variabelwerten sehen.

Das Format der reellen Zahlen wird mit "f" dargestellt.
double Percents=5.5;
//--- real number as a string
string str=StringFormat("Percents = %f",Percents);
//--- output the results
Alert(str);

Nach der Ausführung dieses Codes wird die Variable str folgenden String speichern: "Percents = 5.500000". Die Standardausgabeneinstellung besteht aus drei Dezimalstellen. Sie können die erforderliche Anzahl an Dezimalstellen einstellen:

string str=StringFormat("Percents = %.2f",Percents);

Um dies zu bewerkstelligen, setzen Sie einen Punkt, der ein Dezimalzeichen darstellt, und gleich danach die Anzahl an Dezimalstellen, also 2, wie im Beispiel oben. In diesem Fall wird die Variable str folgenden String enthalten: "Percents = 5.50". Diese Formatierungsoption ist komplett identisch mit der Funktion DoubleToString().

Sie können die absolute Länge einer Zahl festlegen, indem Sie "0" schreiben und eine Zahl, die die Länge der Zahl bestimmt nach "%" und dann die Anzahl an Dezimalstellen festlegen (wenn nötig):

string str=StringFormat("Percents = %06.2f",Percents);

Hier ist die absolute Länge 6 Ziffern, von denen eine verwendet wird um den Punkt darzustellen und zwei weitere stellen zwei Dezimalstellen dar. Daher wird der String, der in der str-Variable gespeichert ist, "Percents = 005.50" sein.

Wenn Sie das Prozentzeichen in einer Ausgabe benötigen, müssen Sie es zweimal schreiben, also "%%", da eines der beiden Zeichen verwendet wird, um Plätze für Werteingaben anzuzeigen.

string str=StringFormat("Percents = %06.2f%%",Percents);

In diesem Fall wird die Variable str "Percents = 005.50%" enthalten:

Sie können die Länge einer Zahl auch bei der Ausgabe ganzzahliger Variablen bestimmen:

int Variable=123;
//--- integer as a string with a set output length
string str=StringFormat("Variable = %05i",Variable);
//--- output the results
Alert(str);

Nach der Ausführung dieses Codes wird die Variable str folgenden String speichern: "Variable = 00123".

Wenn die festgelegte Ziffernanzahl weniger als die Anzahl von Ziffern in der Zahl ist, wird die Ausgabe trotzdem korrekt sein:

string str=StringFormat("Variable = %02i",Variable); 

In diesem Fall wird die Variable str folgenden String enthalten: "Variable = 123", das heißt, die Ausgabezahl wird 3 Ziffern haben, obwohl die festgelegte Länge 2 ist.

Reelle Zahlen können mit wissenschaftlicher Notation ausgegeben werden (Mantisse von sechs Dezimalstellen und Macht) für die wir das Zeichen "e" verwenden:

double Variable=123.456;
//--- real number as a string in scientific notation
string str=StringFormat("Variable = %e",Variable);
//--- output the results
Alert(str);

Nach der Ausführung dieses Codes wird die Variable str "1.234560e+002" enthalten. Sie können auch den Großbuchstaben "E" verwenden, der Ähnliches auslöst wie das kleine "e"; das große "E" ersetzt das kleine "e" in einem formatierten String.

Es gibt auch einen anderen Weg, reelle Zahlen zu formatieren - mit dem Befehl "g", bei dem sechs Ziffern (außer dem Dezimalkomma) ausgegeben werden können. Wenn die Länge des ganzzahligen Teiles einer Zahl mehr als sechs Stellen hat, wird die Zahl mit wissenschaftlicher Notation ausgegeben:

double Variable1=12.3456789;
double Variable2=1234567.89;
//--- get real numbers as strings using "g"
string str1=StringFormat("Variable = %g",Variable1);
string str2=StringFormat("Variable = %g",Variable2);
//--- output the results
Alert(str1+" "+str2);

Im obigen Beispiel wird die str1 Variable "12.3457" enthalten und die str2 Variable wird "1.23457e+006" enthalten. Die Folge wird die gleiche sein wie wenn man das große "G" verwendet; der einzige Unterschied ist dann, dass in der Ausgabe das kleine "g" durch das große "G" ersetzt wird.

Mit der Funktion StringFormat() kann man Darstellungsformate von Zahlen verändern, also Zahlen des Dezimalsystems in Zahlen des Oktalsystems oder Hexadezimalsystems umwandeln. Um eine Zahl in das Oktalsystem umzuwandeln verwendet man das Zeichen "o".

int Variable=17;
//--- real number as a string in the octal system
string str=StringFormat("Variable = %o",Variable);
//--- output the results
Alert(str);

Nach der Ausführung dieses Codes wird die Variable str folgenden String speichern: "Variable = 21" (8*2+1=17).

"X" oder "x" wird verwendet um eine Zahl in das Hexadezimalsystem zu konvertieren. Bei der Verwendung des kleinen "x" wird eine Hexadezimalzahl mit Kleinbuchstaben geschrieben, bei der Verwendung des großen "X" mit Großbuchstaben:

color Variable=clrBlue;
//--- real number as a string in the hexadecimal system
string str=StringFormat("Variable = %x",Variable);
//--- output the results
Alert(str);

Nach der Ausführung dieses Codes wird die Variable str "Variable = ff0000" enthalten.

Ähnlich dazu kann man eine Zahl des Hexadezimalsystems mit dem Zeichen "d" zurück in das Dezimalsystem umwandeln.

int Variable=0x0000ff;
//--- real number as a string in the decimal system
string str=StringFormat("Variable = %d",Variable);
//--- output the results
Alert(str);

Nach der Ausführung dieses Codes ist der String der die Variable str speichern wird die "Variable = 255".

Das Zeichen "s" wird verwendet, um String-Variablen auszugeben:

string Variable="text";
//--- output the string variable
string str=StringFormat("Variable = %s",Variable);
//--- output the results
Alert(str);

Sobald Sie obigen Code ausführen, wird der String, der "Variable = text" enthält, in der Variable str gespeichert.

Manchmal müssen Sie Zahlen justieren bei der Ausgabe in einer Spalte, weil negative Zahlen aufgrund des Minuszeichens nach rechts rutschen. Um positive und negative Zahlen zu justieren, sollten Sie ein Leerzeichen am Anfang des Strings hinzufügen, gleich nach dem Prozentzeichen. In diesem Fall werden negative Zahlen ohne Leerzeichen ausgegeben, nicht wie positive Zahlen, die ein Leerzeichen vorne haben:

int Variable1=1;
int Variable2=-1;
//--- representation of numbers as aligned strings
string str1=StringFormat("Variable1=% 03i",Variable1);
string str2=StringFormat("Variable2=% 03i",Variable2);
//--- output the results
Alert(str1);
Alert(str2);

Nach der Ausführung dieses Codes wird die str1-Variable "Variable1= 01" enthalten (den String mit Leerzeichen), und die str2-Variable wird den String '1.235' wie folgt speichern: "Variable = -01".

Es gibt zwei weitere Funktionen, die ähnlich dem StringFormat() sind. Diese sind PrintFormat() and printf(). Sie machen genau das gleiche. Sie unterscheiden sich nur von der Funktion StringFormat(), in dem sie Text im Journal ähnlich wie die Funktion Print() ausgeben.

Tatsächlich bietet die Funktion StringFormat() viel mehr Funktionalität, während das oben angebotene Material das Minimums dessen darstellt, das gebraucht wird um die Mehrheit der Probleme bezüglich der Zahlenformatierung für die Ausgabe zu lösen.
 

Nachrichten in verschiedenen Sprachen

Die Funktion StringFormat() bietet die Möglichkeit, das Programm mit einem sehr nützlichen Feature zu erweitern, mit dem man Nachrichten in verschiedenen Sprachen ausdrucken kann, je nach Einstellung der Schnittstellen-Sprache im Terminal.

Sie finden die Schnittstellen-Sprache heraus, indem Sie die Funktion TerminalInfoString() mit dem Identikator TERMINAL_LANGUAGE aufrufen. Bei der Ausführung eines Programms bereiten wir einen Format-String vor, abhängig von der Sprache der Schnittstelle, und dann verwenden wir ihn im Programm. Unten ist eine Vorlage eines Expert Advisors, der obige Eigenschaften implementiert hat:

//--- variable for a format string
string FormatString;
//+------------------------------------------------------------------+
//| Handling the Init event                                          |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- get the format string
   FormatString=GetFormatString();
//--- additional call in case you want to ensure that the Expert Advisor operates at least once at weekends
   OnTick();
   return(0);
  }
//+------------------------------------------------------------------+
//| Handling the Tick event                                          |
//+------------------------------------------------------------------+
void OnTick()
  {
   int Variable1,Variable2,Variable3;
   Variable1=MathRand()%10;        // Random number from 0 to 10
   Variable2=MathRand()%10;        // Another random number
   Variable3=Variable1+Variable2; // Sum of numbers
//--- output the results
   Alert(StringFormat(FormatString,Variable1,Variable2,Variable3));
  }
//+------------------------------------------------------------------+
//| Determining the format string                                    |
//+------------------------------------------------------------------+
string GetFormatString(void)
  {
   string Language=TerminalInfoString(TERMINAL_LANGUAGE);
//--- language check
   if(Language=="Russian") return("%i плюс %i равно %i");     // Russian
   if(Language=="Spanish") return("%i más %i es igual a %i"); // Spanish
//--- English - in all other cases
   return("%i plus %i equals %i");
  }

Der Expert Advisor berechnet die Summe von zwei zufälligen Zahlen und gibt die Nachricht bezüglich seiner Aktionen aus, zum Beispiel "1 plus 2 makes 3".

Soweit zur Ausgabe der Strings. Jetzt werden wir mit etwas komplexeren, aber auch interessanteren String-Manipulationen weitermachen.

 

Schlüsselfunktionen für das Arbeiten mit Strings

Wenn ein String durch das Fenster "Programmeigenschaften" eingegeben oder von einer Datei gelesen wird, kann er überflüssige Leerzeichen enthalten. Diese könnten aufgrund sorgloser Unachtsamkeit oder Bequemlichkeit der Benutzer passieren. Vor einer Verwendung der Strings ist es ratsam, Leerzeichen am rechten und linken Ende zu löschen. Für diesen Zweck bietet MQL5 zwei Funktionen: StringTrimLeft() löscht Leerzeichen links und StringTrimRight() löscht Leerzeichen rechts. Zusätzlich zu Leerzeichen entfernen diese Funktionen auch Tabulatoren und Zeichen in neuen Zeilen. Bei der Arbeit mit Strings müssen wir oft Leerzeichen gleichzeitig links und rechts löschen, also wäre eine Funktion die das kann sehr nützlich:

string Trim(string Str)
  {
   StringTrimLeft(Str);
   StringTrimRight(Str);
   return(Str);
  } 

Bei der Eingabe von reellen Zahlen kann der Benutzer oft ein Komma statt eines Punktes setzen. Daher sollten Sie bei der Arbeit mit reellen Zahlen die Möglichkeit anbieten, sowohl Punk und Komma als Dezimalzeichen zu verwenden. Um einen String durch einen anderen zu ersetzen verwenden wir die Funktion StringReplace().

string str="123,456";
//--- replace a comma with a dot
StringReplace(str,",",".");
double Value=StringToDouble(str);
//--- output the results
Alert(DoubleToString(Value));

Sollten Sie das Komma nicht mit dem Punkt ersetzen, wird der Bruchteil der Zahl gekürzt indem ein String in eine Zahl umgewandelt wird.

In manchen Fällen müssen Sie eine Reihe an Leerzeichen mit einem Leerzeichen ersetzen. Um das zu tun, sollten Sie zuerst den Tabulator mit einem Leerzeichen ersetzen und dann zwei Leerzeichen mit einem, bis nur noch ein Leerzeichen übrig ist:

string str="Column-1 \t Column-2 \t Column-3";
//--- replace the tab character with a space
StringReplace(str,"\t"," ");
//--- get one space instead of the series of spaces
while(StringReplace(str,"  "," ")>0){}
//--- output the results
Alert(str);

Der Befehl StringReplace() retourniert die Anzahl an Substitutionen oder -1 im Falle eines Fehlers. Die Schleife geht also weiter und der Befehl gibt einen Wert aus der größer als Null ist bis alle Reihen von Leerzeichen mit einem Leerzeichen substituiert sind. Der Body der Schleife enthält keinen Code. Um die Schleifenbedingung bei jeder Wiederholung zu überprüfen, geben wir den Befehl StringReplace().

Mit dem Befehl StringReplace() können wir Teil-Strings verschiedener Länge ersetzen:

string str="Programming in MQL5!";
//--- replace the substring, output the results
StringReplace(str,"in MQL5","for MetaTrader 5");
Alert(str);
//--- reverse replacement, output the results
StringReplace(str,"for MetaTrader 5","in MQL5");
Alert(str);

Bei der Ausführung dieses Codes hat die Variable str nach der ersten Substitution den String mit "Programmieren für MetaTrader 5", und "Programmieren in MQL5!" nach der zweiten Substitution.

Die Funktion StringFind() wird verwendet, um einen Teil-String zu suchen. Sie gibt den Index des ersten Vorkommen des Teil-Strings in einem String aus. Der erste Parameter in der Funktion ist ein String in dem die Suche ausgeführt wird. Der zweite Parameter bestimmt den Teil-String, in den gespeichert wird, während der dritte Parameter ( optional) die Position bestimmt, bei der die Suche beginnt. Wenn der dritte Parameter nicht festgelegt ist, arbeitet die Funktion, als wäre ihr Wert 0, das heißt, die Suche fängt am Anfang des Strings an. Finden wir also die Position des Teil-Strings "5" im String "Programmieren in MQL5 für MetaTrader 5".

string str="Programming in MQL5 for MetaTrader 5";
//--- get the position of the character
int Pos=StringFind(str,"5");
//--- output the results
Alert(IntegerToString(Pos));

Nach der Ausführung dieses Codes wird der Wert der Pos-Variable 23 sein. Teil-String "5" kommt insgesamt zweimal vor, aber die Funktion gibt die Position des ersten Ereignisses aus. Wenn Sie die Position zählen, indem Sie einfach auf den String schauen, bekommen Sie 24. Aber die Funktion beginnt mit dem Zählen von Null, nicht von Eins. Wenn der Teil-String, in den gespeichert werden soll, nicht gefunden wird, gibt die Funktion -1 aus.

Manchmal muss man eine Position des letzten Vorkommnis des Teil-Strings finden. Dafür müssen wir einen benutzerdefinierten Befehl schreiben: StringFindRev(). Wir fangen mit der Suche nach dem ersten Vorkommen des Teil-Strings an, dann verschieben wir den Start der Suche je nach gefundener Position, zum Beispiel in einer Schleife:

int StringFindRev(string Str,string Find)
  {
//--- the pos variable for the returned value
   int pos;
//--- auxiliary variable initialized to -1,
//--- in case the substring is not found in the string
   int tmp=-1;
//--- loop. It will be executed at least once
   do
     {
      //--- assign the last known position of the substring
      pos=tmp;
      //--- continue searching (using the third parameter of the function)
      tmp=StringFind(Str,Find,tmp+1);
     }
   while(tmp!=-1); // If the substring is not found in the remaining part of the string, the loop 
                   // is terminated and the pos variable stores the last
                   // known position
//--- return the position
   return(pos);
  }
Versuchen wir, diese Funktion zu verwenden:
string str="Programming in MQL5 for MetaTrader 5";
//--- call the function for searching for a position of the last occurrence of the character in the string
int pos=StringFindRev(str,"5");
//--- output the results
Alert(pos);

Nach der Ausführung dieses Codes wird die Pos-Variable den Wert 40 haben.

Der Befehl StringSubstr() wird verwendet, um einen Teil-String einer gegebenen Länge von einer gegebenen Position zu bekommen. Holen Sie den Teilstring der Länge 1 von der Position 23:

string str="Programming in MQL5 for MetaTrader 5";
//--- get the substring of the given length from the given position
string str2=StringSubstr(str,23,1);
//--- output the results
Alert(str2);

Das Ergebnis ist "5".

Da wir nun die Hauptbefehle gesehen haben, verwenden wir sie, um eine erfolgreiche Funktion zu schreiben, mit der man eine gegebene Liste von Zeichen von einem String löschen kann. Die Funktion erhält den Quell-String und einen String, der eine Liste an Zeichen darstellt, die vom Quell-String gelöscht werden.

string TrimL(string Str,string List="\t\n ;")
  {
//--- variable for one character of the Str string
   string ch;
   int Len=StringLen(Str);
   int i=0;
//--- loop iteration over all characters of the Str string
   for(;i<Len;i++)
     {
      //--- the next character of the Str string
      ch=StringSubstr(Str,i,1);
      //--- if this character is not on the List list, the string should start from this position 
      if(StringFind(List,ch,0)==-1)
        {
         break; // terminate the loop
        }
     }
//--- get the substring and return it
   return(StringSubstr(Str,i));
  }

Die Funktion löscht standardmäßig den Tabulator und das Zeichen in der neuen Zeile, genauso wie ein Leerzeichen und den Strichpunkt.

Die gleiche Funktion, um rechts zu löschen:

string TrimR(string Str,string List="\t\n ;")
  {
//--- variable for one character of the Str string
   string ch;
   int Len=StringLen(Str);
//--- characters in the string are numbered from 0, so the last character index is one less than the string length
   int i=Len-1;
//--- loop iteration over all characters of the Str string
   for(;i>=0;i--)
     {
      //--- the next character of the Str string
      ch=StringSubstr(Str,i,1);
      //--- if this character is not on the List list, the string should start from this position 
      if(StringFind(List,ch,0)==-1)
        {
         break; // terminate the loop
        }
     }
//--- get the substring and return it
   return(StringSubstr(Str,0,i+1));
  }

Die Funktion löscht standardmäßig den Tabulator und das Zeichen in der neuen Zeile, genauso wie ein Leerzeichen und den Strichpunkt. Sie kann beim Lesen von CSV-Dateien nützlich sein. In diesen Dateien können eine Menge an Feld-Separatoren (normalerweise Strichpunkte) rechts von einem String sein.

Große und kleine Buchstaben, zum Beispiel "A" und "a", werden von Menschen als das gleiche angesehen, aber für Computer sind es zwei verschiedene Zeichen. Wenn Sie "eurusd" anstatt "EURUSD" schreiben wenn sie mit der Funktion SymbolInfoDouble() Marktdaten anfragen, wird die Funktion nicht den gewollten Wert ausgeben. Das passiert wahrscheinlich, wenn der Symbolname im Eigenschaftsfenster eingegeben wird. Um die Groß- oder Kleinschreibung in MQL5 zu ändern, können Sie den Befehl StringToLower() (um zu Kleinbuchstaben zu wechseln) und StringToUpper() (um zu Großbuchstaben zu wechseln) verwenden.

string str="EuRuSd";
string str1=str;
string str2=str;
//--- change the case of strings
StringToUpper(str1);
StringToLower(str2);
//--- output the results
Alert(str1," ",str2);

Nach der Ausführung dieses Codes wird die str1-Variable den String der "EURUSD" enthält speichern, während die Variable str2 den String mit "eurusd" enthalten wird.

Wenn Sie die Strings vergleichen wollen ohne die Schreibung zu berücksichtigen, passt die Funktion StringCompare() am besten. Die ersten zwei Parameter des Befehls sind die Strings für Vergleiche. Der dritte Parameter bestimmt, ob die Strings verglichen werden sollten, mit Berücksichtigung (wahr) oder Nicht-Berücksichtigung (falsch) der Schreibung:

int Result=StringCompare("eurusd","EURUSD",false);
Alert(Result); 

Wenn die Funktion 0 ausgibt, sind die Strings identische. Die Funktion gibt vielleicht -1 aus, wenn der erste String kleiner als der zweite ist, oder 1 wenn der erste String größer als der zweite ist. "Größer" und "kleiner" bezeichnet den Zustand des Strings bei alphabetischer Ordnung. Der Buchstabe "b" ist größer als der Buchstabe "a":

int Result=StringCompare("a","b",true);
Alert(Result); 

In diesem Fall wird die Funktion -1 ausgeben.

Bevor wir nun mit anderen Funktionen weitermachen, ist es nötig, eine kurze theoretische Abweichung zu machen.
  

Strings, wie sie von Menschen oder Computern gesehen werden

Was ein String für einen Menschen ist, ist klar - ein Text aus Zeichen. Computer sind im Vergleich zu Menschen einfacher, wenn es um die Arbeit mit Zahlen geht. Computer sehen Bilder, Strings und alles andere als Zahlen. Ein String ist ein Array an Zahlen, bei denen ein Zeichen einer Zahl entspricht, oder besser gesagt ein Code, ein anderes Zeichen, ein anderer Code, etc. Diese Codes werden ASCII-Codes genannt (Abk. für American Standard Code for Information Interchange). Wir werden weiterhin die Bezeichnung ASCII verwenden, und damit meinen wir den erweiterten ASCII, der 256 Codes enthält. Also kann man sagen, dass das Computer-Alphabet 256 Zeichen enthält. Genauso wie es verschiedene Alphabete für verschiedene Menschen und Sprachen gibt, haben Computer verschiedene Zeichensätze - Code-Pages. In Russland wird vor allem Windows-1251 verwendet, eine Zeichenkodierung, die lateinische und kyrillische Zeichen enthält, genauso wie Zahlen, Satzzeichen und einige andere Symbole. Abb. 1 zeigt die Codepage Windows-1251:


Abb. 1. Windows-1251 Codepage.

Die ersten 32 Zeichen werden nicht angezeigt, sie sind Steuerzeichen. Sie werden selbst nicht angezeigt, aber die Darstellung von anderen Zeichen, zum Beispiel Tabulatoren (Code 9), Zeilenvorschub (Code 10), etc., wird von ihnen beeinflusst.

Die Enkodierung für zentraleuropäische Sprachen ist Windows-1250 (Abb. 2).


Abb. 2. Windows-1250 Codepage.

Beim Start mit dem Code 192 sollten Sie beachten, dass die Codepage 1251 Buchstaben aus dem russischen Alphabet hat, und die Codepage 1250 Buchstaben mit europäischen diakritischen Zeichen.

256 Zeichen sind sehr wenig. Schwierigkeiten entstehen dann, wenn ein Text in verschiedenen Sprachen geschrieben werden muss, zum Beispiel Russisch und Französisch (das viele diakritische Zeichen hat), oder Englisch und Arabisch (die Zeichen sind ganz anders als in anderen Sprachen). Es gibt auch ein hieroglyphisches Skript, wie in Chinesisch und Japanisch, das Tausende Zeichen hat, und die Schwierigkeiten in diesem Fall sind sehr offensichtlich. Vielleicht müssen Zeichen anders enkodiert werden, die nicht in der Codepage inkludiert sind. Die mit HTML Vertrauten sollten wissen, dass es die Möglichkeit gibt, atypische Zeichen in eine HTML-Seite zu schreiben, zum Beispiel wenn der Code À verwendet wird um À anzuzeigen, und so weiter.

Kürzlich wurde es üblich, die Unicode-Enkodierung zu verwenden, bei der ein Zeichen nicht in einem einzelnen Byte enkodiert wird (von der Zahl 0 zu 255), sondern zwei Bytes, also insgesamt 65536 Zeichen. Dieser Zeichensatz beinhaltet auch Buchstaben aller existierender Alphabete der Welt und sogar die üblichsten Hieroglyphen die in Abb. 3 gezeigt werden (die passenden Fonts sollten trotzdem auf dem Computer installiert werden):

Abb. 3. Buchstaben verschiedener Alphabete und Hieroglyphen.

Abb. 3. Buchstaben verschiedener Alphabete und Hieroglyphen.

Strings werden in MQL5 mit Unicode enkodiert. Anders ausgedrückt wird ein Zeichen in einem String von einer Zahl von 0 bis 65535 dargestellt. Zeichen mit Codes von 0 bis 127 sind gleich wie in ASCII und Unicode. Textdateien können auch Texte enthalten die mit ASCII oder Unicode enkodiert wurden, daher unterscheidet sich MQL5 in der Arbeitsweise mit Strings in ASCII und Unicode.

 

Wie man einen String in ein Array und wieder zurück konvertiert

Bei der Arbeit mit Strings reichen normalerweise die Befehle StringLen(), StringFind(), StringSubst() and StringReplace() um den Großteil der praktischen Aufgaben zu erledigen. Es gibt aber viele Aufgaben, die viel einfacher gelöst werden können, indem man mit Strings als Zahlen arbeitet, so wie Verschlüsselung, Datenkompression, Berechnung von überprüften Werten. Obwohl Aufgaben dieser Art nicht täglich erledigt werden, ist es möglich, dass Sie eines Tages mit ihnen konfrontiert werden. Es gibt viel wichtigere Aufgaben, die erfordern, einen String in einen Array zu konvertieren, zum Beispiel String-Parameter in die Windows-Befehle API (Application Programming Interfaces) zu geben.

Um einen String in einen Unicode-Array zu konvertieren, verwenden wir den Befehl StringToShortArray(), und um ihn in einen ASCII-Array zu konvertieren, verwenden wir den Befehl StringToCharArray().

string str="MetaTrader 5";
//--- converting the string to a Unicode array
short sha[];
StringToShortArray(str,sha);
//--- converting the string to a ASCII array
uchar cha[];
StringToCharArray(str,cha);
//--- flag the difference
bool Dif=false;
//--- compare the arrays element by element
for(int i=0;i<StringLen(str);i++)
  {
   if(sha[i]!=cha[i])
     {
      Dif=true;
     }
  }
//--- output the results
if(Dif) Alert("Different");
else    Alert("Identical");

Wenn die erhaltenen Arrays, die die Befehle StringToShortArray() und StringToCharArray() in den oberen Beispielen verwenden, identisch sind, erscheint ein Fenster mit der Nachricht "identisch" und falls es Schwierigkeiten gab, wird die Nachricht sagen: "anders". Für den String "MetaTrader 5" sind die Arrays identisch, weil der String aus Zeichen mit Zeichencodes bis 127 besteht.

Es ist alles ein bisschen anders mit Zeichencodes über 127. Die Ergebnisse des Befehls StringToShortArray() werden immer und überall die gleichen sein, aber die Ergebnisse des Befehls StringToCharArray() werden von den regionalen Einstellungen des Betriebssystems abhängig sein.

In Windows 7 kann die Sprache des Systems im Bedienfeld ausgewählt werden - Region und Sprache - ändere Sprache.

Schauen Sie sich folgendes Beispiel an: Auf der Codepage 1251 entspricht der Code 192 dem Buchstaben "A" (erster Buchstabe des russischen Alphabets), während der selbe Code in der Enkodierung 1250 dem Buchstaben "Ŕ" entspricht (einer der am meisten verwendeten Buchstaben des tschechischen Alphabets). Bei der Verwendung der Funktion StringToShortArray() wird der Buchstabe "A" immer den Code 1040 haben, und der Buchstabe "Ŕ" den Code 340. Wenn das System auf Russisch eingestellt ist und der Befehl StringToCharArray() gegeben wird, entspricht der Buchstabe "A" dem Code 192 (korrekt) während der Buchstabe "Ŕ" dem Code 82 entspricht (Latein "R"). Wenn das System auf Tschechisch eingestellt ist, entspricht der Buchstabe "A" dem Code 63 (Fragezeichen) während der Buchstabe "Ŕ" dem Code 192 entspricht (korrekt). Diakritische Zeichen werden durch ähnliche lateinische Zeichen ersetzt, während nicht so übliche Zeichen durch das Fragezeichen ersetzt werden.

Beachten Sie die Größe des Strings und die resultierenden Arrays:

int StrLen=StringLen(str);
int shaLen=ArraySize(sha);
int chaLen=ArraySize(cha);
//--- output the lengths
Alert(StringFormat("%i, %i, %i",StrLen,shaLen,chaLen));

Die Anzahl an Elementen in Arrays ist um eines größer als die Anzahl der Zeichen in einem String. Das kommt daher, weil das Ende des Strings mit dem Zeichen mit dem Code 0 markiert ist. Dieses Zeichen wird im String nicht dargestellt, aber es sagt dem Computer, dass der String der dargestellt wird, hier endet. Datenaustausch wird nicht immer mit einem Byte ausgeführt (Zeichen) wenn die Menge der Stringlänge entspricht, aber das Zeichen mit dem Code 0 ermöglicht es ihnen, das Ende des Strings zu bestimmen. Die selbe Null kann auch Probleme verursachen, zum Beispiel wenn ein bestimmtes Zeichen zum Zeichen mit dem Code 0 konvertiert wird bei der Verschlüsselung oder Kompression eines Algorithmus. Wenn Sie ein Array hier wieder in einen String rückumwandeln, wird der String nicht komplett sein. Aufgaben dieser Art erfordern den Gebrauch von Spezialtricks, aber dies geht über diesen Artikel hinaus.

Die Rückumwandlung eines Array in einen String ist mit den Funktionen ShortArrayToString() und CharArrayToString() möglich:

//--- convert an array of Unicode codes to a string
short sha[]={85,110,105,99,111,100,101};
string str1=ShortArrayToString(sha);
//--- convert an array of ASCII codes to a string
uchar cha[]={65,83,67,73,73};
string str2=CharArrayToString(cha);
//--- output the results
Alert(str1+" "+str2);

Als Ergebnis des obigen Codes speichert die Variable str1 den String "Unicode" und str2 speichert den String "ASCII".

Es gibt zwei ähnliche Funktionen: ShortToString() und CharToString(). Sie wandeln einzelne Variablen des Typs short oder char in einen String der nur aus einem Buchstaben besteht. Der Befehl CharToString() ist von großem praktischen Wert. Ein graphisches Objekt, mit dem Sie verschiedene Symbole darstellen können, OBJ_ARROW, ist vertikal in der Preisachse verankert und horizontal in der Zeitachse, also wechseln die Symbole, wenn Sie durch die Chart scrollen. OBJ_LABEL und die Font Wingdings ermöglichen es uns, verschiedene Symbole darzustellen die in den Koordinaten des Bildschirms verankert sind und die es uns erlauben, verschiedene Informationspanels zu erstellen. Wir finden das benötigte Symbol in der Wingdings-Symbol-Tabelle, konvertieren seinen Code in einen String, der nun mit dem graphischen Objekt OBJ_LABEL dargestellt wird:

   ObjectCreate(0,"lbl",OBJ_LABEL,0,0,0);           // create the LABEL graphical object
   ObjectSetInteger(0,"lbl",OBJPROP_XDISTANCE,100);   // set the X-coordinate
   ObjectSetInteger(0,"lbl",OBJPROP_YDISTANCE,100);   // set the Y-coordinate
   ObjectSetInteger(0,"lbl",OBJPROP_FONTSIZE,20);     // set the size
   ObjectSetString(0,"lbl",OBJPROP_FONT,"Wingdings"); // set the Wingdings font
   string Icon=CharToString(37);                   // 37 - the bell
   ObjectSetString(0,"lbl",OBJPROP_TEXT,Icon);       // set the displayed text

Als Ergebnis dieses Codes werden Sie das Symbol einer Glocke im Diagramm sehen. Die Glocke wird an diesem Platz bleiben, wenn Sie durch das Diagramm scrollen.

Zwei weitere Funktionen für die Arbeit mit Zeichencodes sind StringGetCharacter() und StringSetCharacter(). Sie arbeiten mit Unicode Codes. Die Funktion StringGetCharacter() ermöglicht es Ihnen, den Zeichencode in einer bestimmten Position des Strings zu bekommen:

string str="L5";
//--- get the Unicode code of the character at the given position in the string
ushort uch1=StringGetCharacter(str,0);
ushort uch2=StringGetCharacter(str,1);
//--- output the results
Alert(StringFormat("%i, %i",uch1,uch2));

Nach der Ausführung dieses Codes speichert die Variable uch1 den Wert 76 und uch2 speichert 53.

Der Befehl StringGetCharacter() ermöglicht es Ihnen, den Zeichencode in einer bestimmten Position des Strings zu bekommen und Zeichen an das Ende eines Strings zu setzen:

string str="MQ5";
//--- replace the character at the given position in the string with the Unicode character corresponding to the passed code
StringSetCharacter(str,2,76);
Alert(str);
//--- add the Unicode character corresponding to the passed code to the end of the string
StringSetCharacter(str,3,53);
Alert(str);

Bei der Ausführung dieses Codes speichert die Variable str statt "MQ5" zuerst "MQL" und dann "MQL5".

 

API-Befehl eingeben

Einige API-Befehle verwenden String-Parameter als Variablen. Zum Beispiel verwendet der Befehl für Drittparteien-Anwendungen WinExec einen Array des Typs uchar als ersten Parameter.

#import "kernel32.dll"
int WinExec(uchar &Path[],int Flag);
#import 

Versuchen wir nun, notepad.exe auszuführen, ein Standardprogramm in Windows. Wandeln Sie den Pfad zu Notepad um in ein Array des uchar-Typs:

string PathName="C:\\WINDOWS\\notepad.exe";
uchar ucha[];
StringToCharArray(PathName,ucha);
int x=WinExec(ucha,1); 

Dieser Befehl sollte den Notepad Text Editor öffnen.

Ein anderes Beispiel von String-Parametern in API-Befehlen ist die Funktion MessageBoxW, die eine Nachricht im Fenster ausdruckt mit Unicode. Aus diesem Grund geben wir Arrays des ushort-Typs als Parameter:

#import "user32.dll"
int MessageBoxW(int hWnd,ushort &szText[],ushort &szCaption[],int nType);
#import

Nun verwenden wir diesen Befehl, um eine Nachricht in einem Fenster zu drucken:

ushort arr[];
ushort capt[];
//--- convert
StringToShortArray("Programming in MQL5 for MetaTrader 5.",arr);
StringToShortArray("Message",capt);
//--- print the message
MessageBoxW(0,arr,capt,0);

Als Ergebnis dieses Codes werden Sie ein Fenster mit der folgenden Nachricht sehen: "Programmieren in MQL5 für MetaTrader 5".

Es sollte klargestellt werden, dass die Verwendung von Arrays des ushort Typs im obigen Beispiel nicht notwendig ist und Sie einfach Strings als Funktionsparameter geben können:

#import "user32.dll"
int MessageBoxW(int hWnd,string szText,string szCaption,int nType);
#import
//+------------------------------------------------------------------+
//| Function for running the script                                  |
//+------------------------------------------------------------------+
void OnStart()
  {
   MessageBoxW(0,"Programming in MQL5 for MetaTrader 5","Message",0);
  }

Das Ergebnis des Codes wird das gleiche sein wie oben. Aber Sie werden nicht dazu in der Lage sein, Arrays des uchar-Typs als Befehlsparameter zu verwenden, um die richtige Nachricht zu drucken:

#import "user32.dll"
int MessageBoxW(int hWnd,uchar &szText[],uchar &szCaption[],int nType);
#import
//+------------------------------------------------------------------+
//| Function for running the script                                  |
//+------------------------------------------------------------------+
void OnStart()
  {
   uchar arr[];
   uchar capt[];
//--- convert
   StringToCharArray("Programming in MQL5 for MetaTrader 5.",arr);
   StringToCharArray("Message",capt);
//--- print the message
   MessageBoxW(0,arr,capt,0);
  }

Der Code wird fehlerfrei ausgeführt und ein Fenster wird erscheinen, aber die Nachricht wird deformiert sein.

Wenn es nötig ist, einen String in der ASCII-Enkodierung auszudrucken (zum Beispiel wenn Sie bereits einen Array des uchar-Typs haben), gibt es eine ähnliche Funktion: MessageBoxA. Um die Nachricht korrekt anzuzeigen, sollten nur Arrays des uchar-Typs zur Funktion als Stringparameter gegeben werden. Importieren Sie nun diese Funktion und rufen Sie sie auf, um die Nachricht zu drucken:

#import "user32.dll"
int MessageBoxA(int hWnd,uchar &szText[],uchar &szCaption[],int nType);
#import
//+------------------------------------------------------------------+
//| Function for running the script                                  |
//+------------------------------------------------------------------+
void OnStart()
  {
   uchar arr[];
   uchar capt[];
//--- convert
   StringToCharArray("Programming in MQL5 for MetaTrader 5",arr);
   StringToCharArray("Message",capt);
//--- print the message
   MessageBoxA(0,arr,capt,0);
  }

Wieder bekommen wir die korrekte Nachricht: "Programming in MQL5 for MetaTrader 5".

Es gibt also 2 Optionen für einige der WinAPI-Befehle, die mit Strings funktionieren - die Option für die Arbeit mit ASCII-Strings und die Option für die Arbeit mit Unicode Strings.

Um diese Funktionen aufzurufen, aktivieren Sie DLLs in den Terminal-Einstellungen (Terminal - Hauptmenü - Werkzeuge - Optionen - Expert Advisor - DLL-Import erlauben) oder überprüfen Sie "DLL-Importe erlauben" im Abhängigkeits-Tabulator des Fensters Eigenschaften bei der Ausführung eines Skripts, Expert Advisors oder Indikators. Präzisieren Sie das entsprechende Skript property, um die Öffnung des Fensters "Eigenschaften" für das Skript zu aktivieren.

#property script_show_inputs

 

Unlimitierten Parameter-Input

Der Benutzer gibt Parameter im Fenster "Eigenschaften" ein und trennt sie mit einem Strichpunkt:

input string Lots="0.1; 0.2; 0.3; 0.5";

Wir müssen diesen String in eine Array von Variablen des Double Typs konvertieren.

Ein String kann in MQL5 mit der Funktion StringSplit() geteilt werden. Der erste Parameter in der Funktion ist ein String, der zweite ein ASCII-Code des Separators und der dritte ein Array, der die Ergebnisse des Funktionsdurchlaufs speichert. Es gibt einen sehr einfachen Weg, den ASCII-Code den Sie brauchen zu bestimmen, um die benötigten Zeichen in einfache Anführungszeichen zu setzen:

int Code='A';
Alert(IntegerToString(Code)); 

Durch diesen Code wird die Code-Variable den Wert 65 speichern, was dem ASCII-Code des lateinischen Zeichen "A" entspricht.

Stellen wir die Lösung dieses Problems als einen separaten Befehl dar, damit wir ihn einfach verwenden können wenn nötig. Der erste Parameter, der in den Befehl eingegeben wird, ist ein String, und der zweite ein Array. Der Code dieses Befehls ist unten mit detaillierten Kommentaren gegeben, daher braucht man keine weiteren Erklärungen:

int ParamsToArray(string Str,double &Params[])
  {
//--- delete spaces at the ends
   StringTrimLeft(Str);
   StringTrimRight(Str);
//--- if the string is empty
   if(StringLen(Str)==0)
     {
      ArrayFree(Params); // free the array
      return(0);         // function operation complete
     }
//--- auxiliary array
   string tmp[];
//--- split the string
   int size=StringSplit(Str,';',tmp);
//--- delete spaces at the ends for each element of the array
   for(int i=0;i<size;i++)
     {
      StringTrimLeft(tmp[i]);
      StringTrimRight(tmp[i]);
     }
//--- delete empty elements from the array (user could accidentally 
//--- put the separator two times in a row or at the end of the string)
   for(int i=size-1;i>=0;i--)
     {
      if(StringLen(tmp[i])==0)
        {
         ArrayCopy(tmp,tmp,i,i+1);
         size--; // array size reduced
        }
     }
//--- scale the array according to the new size
   ArrayResize(tmp,size);
//--- replace commas with dots
   for(int i=0;i<size;i++)
     {
      StringReplace(tmp[i],",",".");
     }
//--- prepare the array to be returned
   ArrayResize(Params,size);
//--- convert all elements to the double type and fill the array to be returned 
   for(int i=0;i<size;i++)
     {
      Params[i]=StringToDouble(tmp[i]);
     }
//--- the function returns the number of parameters
   return(size);
  }

 

Wie man Strings in verschiedene Variablen konvertiert

Die Funktion ParamsToArray() verwendet die Standardfunktion StringToDouble() um den String in die Variable des Double Typs zu konvertieren. Der selbe Befehl wird für die Konvertierung des Float Typs verwendet. Es gibt Standardbefehle, die für die Konvertierung von anderen Variabeltypen verwendet werden.

Der Befehl StringToInteger() konvertiert einen String in eine ganzzahlige Variable:

string Str="12345.678";
//--- convert the string to an integer
long Val=StringToInteger(Str);
//--- inverse convert and output the results
Alert(IntegerToString(Val));

Nach der Ausführung dieses Codes wird die Val-Variable den Wert 12345 speichern. Der Bruchteil ist einfach verkürzt.

Der Befehl StringToTime() konvertiert einen String, der die Zeit ausdrückt, zum relevanten numerischen Wert. Wenn die Zeit nicht präzisiert wird, ist der Standardwert "00:00":

string Str1="2012.11.02 22:00";
string Str2="2012.01.01";
//--- convert the string expression of time to the datetime type
datetime DateTime1=StringToTime(Str1);
datetime DateTime2=StringToTime(Str2);

Mit dem Befehl StringToColor() kann man einen Farbnamen (Standardwebfarbe) in den relevanten numerischen Wert konvertieren, oder einen String aus RGB-Komponenten:

string Str1="clrYellow";
string Str2="255,255,0";
color Color1=StringToColor(Str1);
color Color2=StringToColor(Str2); 

Es gibt einen weiteren Weg, Strings in Datumsangabe und Farbtypen zu konvertieren. Er wird verwendet, um bestimmte Werte Variablen zuzuordnen.

datetime DateTime=D'2012.11.02 22:00';
color Color=C'255,255,0'; 

"D" wird vor dem String, der die Zeit ausdrückt, geschrieben, und das Datum selbst ist in einfache Anführungszeichen gesetzt. Vor dem String, der Farben ausdrückt, befindet sich der Buchstabe "C" und die RGB-Komponenten sind in einzelne Anführungszeichen gesetzt und werden von einem Komma getrennt.

 

Aktivierung von Benachrichtigungen

Der Benutzer gibt eine Reihe an Zeichen ein, die einen bestimmten Typ von Benachrichtigung aktivieren. Mit dieser Methode kann man verschiedene Kombinationen von Benachrichtigungen aktivieren. Die Alarm-Benachrichtigung entspricht einem "a", Benachrichtigungen mit Ton einem "s", E-mail-Benachrichtigungen einem "e" und Push-Nachrichten einem "p". Außerdem können Sie 1 oder 0 hinzufügen, um den Balken zu bezeichnen, auf dem Signale markiert sind (was bei Indikatoren nützlich sein kann). Der Code wird als Funktion dargestellt, deren erster Parameter ein String ist, der von der Shift-Variable (Zahl des Balkens) und zurückgegeben wird durch Variablen des Bool-Typs, die anderen Notifikationsmethoden entsprechen: Dieser Code wird mit detaillierten Kommentaren angeboten:

void NotifyOnOff(string Str,int &Shift,bool &Alerts,bool &Sounds,bool &EMail,bool &Push)
  {
//--- Convert the string to lower case to allow the user
//--- to use both lowercase and uppercase characters.
   StringToLower(Str);
//--- search for characters in the string
   Alerts=(StringFind(Str,"a")!=-1);    // "a" found
   Sounds=(StringFind(Str,"s")!=-1);    // "s" found
   EMail=(StringFind(Str,"e")!=-1);     // "e" found
   Push=(StringFind(Str,"p")!=-1);      // "p" found
//--- search for zero
   if(StringFind(Str,"0")!=-1) Shift=0;  // "0" found in the string
   else                       Shift=1; // by default
  }

Statt fünf Variablen im Fenster Eigenschaften wird ein einzelnes reichen.  

 

String-Puffer

Es fehlen immer noch drei Standardbefehle in unserem Bericht: StringInit(), StringFill() und StringBufferLen().

Der Befehl StringInit() schreibt einen String mit identischen Zeichen in die Zahl, die festgelegt wurde:

string str;
StringInit(str,10,'|');
Alert(str); 

Nach der Ausführung dieses Codes wird die Variable str folgenden String speichern: "||||||||||". Das Zeichen wird mit der Enkodierung ASCII bestimmt, das heißt, die Zeichen müssen in einfache Anführungszeichen gesetzt werden.

Der Befehl StringInit() schreibt einen String mit identischen Zeichen, ohne die Stringgröße zu ändern. Um das letzte Beispiel weiterzuführen:

StringFill(str,'/');
Alert(str); 

Nach dieser Aktion wird die Variable str folgenden String speichern:"//////////".

Versuchen wir nun, einen String mit dem Zeichencode 0 zu schreiben (Ende des Strings).

StringFill(str,0); 
Überprüfen Sie die Stringgröße:
int Length=StringLen(str);
Alert(IntegerToString(Length)); 

Die Größe ist 0 und das Zeichen mit dem Code 0 ist am Anfang des Strings. Überprüfen Sie die Puffergröße:

int BLength=StringBufferLen(str);
Alert(IntegerToString(BLength)); 

Die Puffergröße ist anders als 0 und überschreitet die Größe des ersten Strings. Der dem String zugeordnete Speicher ist groß genug. Bei der Zuordnung eines Wertes zum String innnerhalb der Puffergröße wird Speicherzuteilung nicht benötigt und der Wert wird sehr schnell zugeordnet. Um sicherzustellen, dass die Puffergröße nicht reduziert wurde, sollte der neue Wert zum String hinzugefügt werden, anstatt ihm zugeteilt zu werden:

str+="a"; 

Die Stringlänge beträgt nun 1, aber die Puffergröße ist die selbe geblieben. So können Sie das Verarbeiten von Strings einigermaßen beschleunigen. Ein String kann gelöscht werden, indem man das Zeichen 0 am Anfang des Strings einsetzt.

StringSetCharacter(str,0,0); 

 

Fazit

Man würde annehmen, dass das Thema dieses Artikel nicht so wichtig ist, da er für den Hauptzweck der MQL5-Sprache, nämlich der Entwicklung eines Expert Advisors, nur wenig relevant ist. Es ist jedoch ein ziemlich umfassender Artikel, der von einer großen Auswahl an Funktionen für die Arbeit mit Strings inspiriert wurde, die die Sprache bietet. Es ist nicht unwahrscheinlich, dass Sie bei der Programmierung eines Expert Advisors und Indikators nichts mit Strings zu tun haben werden, aber vielleicht wird es doch eines Tages verlangt. Nach der Lektüre dieses Artikels können sie gut vorbereitet mit Strings arbeiten wenn nötig, ohne Zeit mit dem Lernen der Funktionen zu verschwenden. Sie werden in der Lage sein, ganz einfach zu tun, was verlangt wird.

Lassen Sie uns die Information in diesem Artikel wiederholen, indem wir die Funktionen nach ihrem Zweck, ihrer Wichtigkeit und ihrer Gebrauchshäufigkeit ordnen.

  1. StringLen(), StringFind(), StringSubstr(), StringReplace() and StringSplit() sind Schlüsselfunktionen, die zur Bestimmung von Stringlänge und zur Teil-String-Suche verwendet werden und mit denen man einen Teil-String ersetzen, sowie einen String teilen kann.
     
  2. StringTrimLeft(), StringTrinRight(), StringToLower() and StringToUpper() sind sehr nützliche Hilfsfunktionen, die zum Löschen von Leerzeichen an den Enden verwendet werden, und um die Groß- und Kleinschreibung zu ändern.
     
  3. ColorToString(), DoubleToString(), EnumToString(), IntegerToString(), TimeToString() und StringFormat() sind Funktionen, die numerische Variablen in einen String konvertieren.
     
  4. StringToColor(), StringToDouble(), StringToInteger(), StringToTime() und StringCompare() sind Funktionen, die einen String in eine numerische Variable konvertieren.
     
  5. StringAdd() und StringConcatenate() sind Funktionen, mit denen man Strings platzsparend zusammenfügen und kombinieren kann.
     
  6. ShortToString(), ShortArrayToString(), StringToShortArray(), genauso wie CharToString(), CharArrayToString() und StringToCharArray() sind Funktionen mit Strings als Arrays die bei Aufgaben, die komplexe Stringmanipulationen erfordern, nützlich sein können. Von obiger Liste können wir zwei Funktionen als sehr wichtig markieren:  

    • CharToString() wird für die Arbeit mit graphischen Objekten verwendet, zusammen mit Wingdings,
    • CharArrayToString() wird verwendet, um einen String-Parameter bei der Ausführung von API-Funktionen vorzubereiten.

  7. StringSetCharacter(), StringGetCharacter(), StringInit(), StringFill() und StringBufferLen() sind Funktionen zweiter Ordnung.

 

Angehängte Dateien

  1. IncStrFunctions.mqh enthält die Funktionen Trim(), StringFindRev(), TrimL(), TrimR(), ParamsToArray() und NotifyOnOff().
  2. eMultiLanguageMessage.mq5 ist ein Beispiel eines Expert Advisors mit Nachrichten in verschiedenen Sprachen.

Übersetzt aus dem Russischen von MetaQuotes Ltd.
Originalartikel: https://www.mql5.com/ru/articles/585

Beigefügte Dateien |
Maschinelles Lernen: Wie Support Vector Machines beim Handeln verwendet werden können Maschinelles Lernen: Wie Support Vector Machines beim Handeln verwendet werden können
Support Vector Machines wurden lange in Bereichen wie Bioinformatik und angewandter Mathematik verwendet, um komplexe Datensätze zu evaluieren und nützliche Muster für die Datenklassifikation zu extrahieren. In diesem Artikel wird besprochen, was eine Support Vector Machine ist, wie sie arbeitet und warum sie so nützlich bei der Extraktion komplexer Muster ist. Danach werden wir untersuchen, wie sie auf dem Markt angewandt werden können und vielleicht beim Handeln Ratschläge geben. Mit dem "Support Vector Machine Learning Tool" bietet der Artikel Beispiele, anhand derer Leser mit ihrem eigenen Handeln experimentieren können.
Wie teste ich einen Handelsroboter vor dem Kauf Wie teste ich einen Handelsroboter vor dem Kauf
Der Kauf eines Handelsroboters hat bestimmte Vorzüge gegenüber ähnlichen Möglichkeiten - ein automatisiertes System kann direkt im MetaTrader5-Terminal getestet werden. Vor dem Kauf kann und soll ein Expert Advisor sorgfältig in allen ungünstigen Modi im eingebauten Strategietester ausgeführt werden, um das System komplett zu verstehen.
Spontane Änderung der Expert-Advisor-Parameter vom Bedienfeld aus Spontane Änderung der Expert-Advisor-Parameter vom Bedienfeld aus
Dieser Artikel zeigt anhand eines Beispiels die Implementierung eines Expert Advisors, dessen Parameter vom Bedienfeld aus kontrolliert werden können. Bei einer spontanen Änderung der Parameter schreibt der Expert Advisor die Werte vom Infofeld in eine Datei, um sie später von dieser Datei zu lesen und sie im Feld darzustellen. Dieser Artikel ist interessant für alle, die manuell oder semi-automatisch handeln wollen.
Wie man ein Anbieter von Signalen für MetaTrader 4 und MetaTrader 5 wird Wie man ein Anbieter von Signalen für MetaTrader 4 und MetaTrader 5 wird
Möchten Sie Ihre Handelssignale anbieten und Gewinne erzielen? Registrieren Sie sich auf der Website MQL5.com als Verkäufer, geben Sie Ihr Handelskonto an und bieten Sie Händlern ein Abonnement an, um Ihre Handelsgeschäfte zu kopieren.