Ok, ich sehe, Sie haben einen Expertenberater für diese Zwecke geschrieben, und es ist ohne Empfehlungen geschrieben, die ich in Artikel gepostet habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich sieht es so aus.
... your code
int DB = -1; // Datenbankbezeichner//--
... your code
intOnInit()
{
DB = MySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag);
if (DB != -1)
{
// Verbindung erfolgreich!// hier müssen Sie die Logik für die Tabellenerstellung definieren
}
return(INIT_SUCCEEDED);
}
voidOnDeinit(constint reason)
{
MySqlDisconnect(DB);
}
voidOnTick()
{
// erster Befehl.if (DB==-1) return; // keine Aktion durchführen, wenn keine Verbindung besteht// hier Ihr Code ohne cMySqlConnect-Aufruf
}
You have to rebuild your code based on the requirements of project, as I see the currently there is no clear logic, everything messed up.
Ok, ich sehe, dass Sie einen Expert Advisor für diesen Zweck geschrieben haben, und er ist ohne die Empfehlungen geschrieben, die ich in meinem Artikel geschrieben habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich wird es so aussehen.
Danke, ich werde es noch einmal versuchen und das Ergebnis zurückgeben.
Ok, ich sehe, dass Sie einen Expert Advisor für diesen Zweck geschrieben haben, und er ist ohne die Empfehlungen geschrieben, die ich in meinem Artikel geschrieben habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich wird es so aussehen.
Ich änderte Schritt für Schritt, aber das Problem ist immer noch vorhanden, wenn der Experte in einem mt4 für vier oder mehr Symbole verwenden. es drucken " Access violation lesen 0x0000000B in '... .MQLMySQL.dll' "
Der Code ist wie folgt
<--
#include <MQLMySQL.mqh
int MySqlErrorNumber; // aktuelle MySQL-Fehlernummer
Ok, ich sehe, dass Sie einen Expert Advisor für diesen Zweck geschrieben haben, und er ist ohne die Empfehlungen geschrieben, die ich in meinem Artikel geschrieben habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich wird es so aussehen.
Das Problem ist, dass es nicht in einem mt4 für mehr als zwei Symbole verwendet werden kann, wenn es nur in einem Symbol verwendet wird, ist es normal. Wenn es in vier oder mehr Symbolen verwendet wird, läuft es gut, aber nach ein paar Minuten, druckt es das Problem "OnTick()". Minuten wird das Problem "Access violation read to 0x0000000B in '...MQLMySQL.db'" gedruckt. .MQLMySQL.dll'"
Die exambles ist alle Skripte, es ist nur ein Mal ausgeführt, Sie können versuchen, ein Experten rufen Sie die dll in vier oder mehr Symbole in ein oder zwei mt4, Sie können das Problem finden.
Wäre die dll braucht ein memeoy Release oder garbe Sammlung?
MFC entsorgt Lecks vorzeitig, wenn es beendet wird, anstatt darauf zu warten, dass der CRT Lecks nach der Zerstörung st atischer Daten entsorgt, und dies führt zu ο falschen Leckberichten für Objekte, die Speicher zugewiesen haben, bevor MFC initialisiert wurde, und die daher nach MFC zerstört werden nbsp; falsche Leckmeldungen für Objekte, die Speicher zugewiesen haben, bevor die MFC initialisiert wurde, und die daher nach dem Beenden der MFC zerstört werden. Dies wird häufig beobachtet, wenn die MFC-DLL in einem Programm verwendet wird, das auch die C++-Laufzeit-DLLverwendet .
Anhand des Codes, den Sie uns zur Verfügung gestellt haben, vermute ich, dass Sie neu in MQL sind.
Es tut mir leid, ich habe keine Zeit, Sie zu unterrichten, aber ich habe Zeit, die Software zu testen, die ich entwickelt habe.
Es tut mir leid, dass ich keine Zeit habe, Ihnen etwas beizubringen, aber ich habe Zeit, die Software zu testen, die ich entwickelt habe.
Ich habe einen Test-EA für Sie gebaut, der auf Ihrer Logik basiert: jede Tabelle ist für jedes Währungspaar definiert und kann die Online-Marktdaten für verschiedene Konten halten.
Sie können die Logs einsehen, kein einziger Fehler "Access violation..." wurde ausgelöst. Sie können die Protokolle einsehen, kein einziger Fehler "Access violation..." wurde ausgelöst.
Das Problem liegt nicht in der MQLMySQL-Bibliothek.
EA testen.
//+------------------------------------------------------------------+//|& nbsp;   ; DFTest.mq4 |//|& nbsp; Copyright 2014, MetaQuotes Software Corp.//|& nbsp;   http://www.mql5.com |//+------------------------------------------------------------------+#property copyright"Copyright 2014, MetaQuotes Software Corp."#property link"http://www.mql5.com"#property version"1.00"#property strict#include <MQLMySQL.mqh>
inputstring Host = "localhost";
inputstring User = "root";
inputstring Password = "ioctrl";
inputstring Database = "mysql";
inputint Port = 3306;
inputstring Socket = "";
inputint ClientFlag = 0;
inputint Timer = 1; // Timer (Sekunden) jetzt nicht verwendetint DB;
intOnInit()
{
SQLTrace = true; // um zu sehen, dass alle Abfragen an die Datenbank gesendet werden würdenEventSetTimer(Timer);
DB = MySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag);
if( DB == -1 )
{
Print("Database is not connected! Error: ", MySqlErrorDescription);
return (INIT_FAILED);
}
// Tabelle erstellen, falls nicht vorhandenstring cmd;
cmd = "CREATE TABLE IF NOT EXISTS `" + Symbol() + "` (id int NOT NULL AUTO_INCREMENT PRIMARY KEY, AccountNumber int, "
+ "Symbol char(20), Bid double, Ask double, Spread double, "
+ "Memo char(50), "
+ "Time datetime) ENGINE=MEMORY DEFAULT CHARSET=utf8";
if (!MySqlExecute(DB, cmd))
{
Print ("Table creation error: ",MySqlErrorDescription);
return (INIT_FAILED);
}
return(INIT_SUCCEEDED);
}
voidOnDeinit(constint reason)
{
MySqlDisconnect(DB);
EventKillTimer();
}
voidOnTimer()
{
// Sie sollten OnTick niemals von OnTimer aus aufrufen und umgekehrt.// das Ziel dieser 2 Funktionen ist unterschiedlich
}
voidOnTick()
{
int account;
string symbol;
double spread;
string Query, cmd;
int Cursor;
int Rows;
if (DB == -1)
{
Comment("Database is not connected ... ");
return;
}
if ( IsExpertEnabled() && IsConnected() && AccountNumber() > 0 )
{
account = AccountNumber();
symbol = "`"+Symbol()+"`"; // wenn Sie ihn als Tabellennamen verwenden wollen, müssen Sie ihn in Anführungszeichen setzen, wie es in MySQL-Datenbanken üblich ist
spread = (Ask - Bid);
// Möglicherweise wäre es besser, etwas wie dieses zu verwenden: admission = MarketInfo(symbol, MODE_SPREAD);
Query = "SELECT * FROM " + symbol + " where AccountNumber = " + (string)account;
Cursor = MySqlCursorOpen(DB, Query);
if (Cursor >= 0)
{
Rows = MySqlCursorRows(Cursor);
if ( Rows > 0 )
{
cmd = "update " + symbol + " set Bid = "+(string)Bid + ", Ask = " + (string)Ask
+ ", Spread = " + DoubleToStr(spread, Digits)
+ ", Time = '" + TimeToString(TimeLocal(), TIME_DATE|TIME_SECONDS) +"' where AccountNumber = " + (string)account;
}
else
{
cmd = "INSERT INTO " + symbol + "(AccountNumber, Symbol, Bid, Ask, Spread, Memo, Time) VALUES ("
+ (string)account + ", \'" + symbol + "\', "+DoubleToStr(Bid,Digits)+","+ DoubleToStr(Ask,Digits) + "," + DoubleToStr(spread, Digits)
+ ", \'" + AccountCompany() +"\', \'"+TimeToString(TimeLocal(), TIME_DATE|TIME_SECONDS)+"\')";
}
if (!MySqlExecute(DB, cmd))
{
Print("Updating error: ",MySqlErrorDescription);
Print (cmd);
}
MySqlCursorClose(Cursor);
}
}
}
Das ist die richtige Logik bei der Verwendung der Bibliothek.
Aufgrund der Optimierung können Sie sogar keine SELECT-Anweisung verwenden, sondern nur eine UPDATE-Anweisung ausführen und dann prüfen, ob (MySqlRowsAffected()==0) bedeutet, dass keine Zeile aktualisiert wurde. Sie haben ~100% der Aktualisierungen, also wenden Sie die INSERT-Anweisung an.
Sie haben ~100% der Aktualisierungen, also kann dieser Workaround die Leistung erhöhen und den Netzwerkverkehr reduzieren.
Und am Ende, vollständige Quellcodes des Projekts (einschließlich DLL-Entwicklung) wurde an den Artikel angehängt, können Sie es auf Ihre eigene Weise zu ändern.
Wenn Sie das Problem ohnehin in der MqlMySQL.DLL finden, können Sie es selbst debuggen und beheben.
Ihre Codes helfen mir so sehr, ich kann so viel Zeit sparen. Ich habe versucht, INSERT, SELECT, UPDATE und DELETE Abfrage erfolgreich zu tun. Wenn ich nicht falsch liege, wird der "Cursor" nur für SELECT-Abfragen benötigt ??
= pedma
//+------------------------------------------------------------------+//|MySQL-006.mq4 |//|Copyright 2014, Eugene Lugovoy |//| http://www.fxcodexlab.com |//| Select, Insert, Update & Delete Abfrage|//| geändert von: pedma|//+------------------------------------------------------------------+#property copyright"Copyright 2014, Eugene Lugovoy."#property link"http://www.fxcodexlab.com"#property version"1.00"#property strict#include <MQLMySQL.mqh>
string INI;
//+------------------------------------------------------------------+//| Skript-Programmstartfunktion|//+------------------------------------------------------------------+voidOnStart() {
string Host, User, Password, Database, Socket; // Datenbank-Anmeldeinformationenint Port,ClientFlag;
int DB; // DatenbankbezeichnerPrint (MySqlVersion());
INI = "C:\\This\\Must\\be\\Real\\Path\\To\\MyConnection.ini";
// Lesen der Datenbankanmeldedaten aus der INI-Datei
Host = ReadIni(INI, "MYSQL", "Host");
User = ReadIni(INI, "MYSQL", "User");
Password = ReadIni(INI, "MYSQL", "Password");
Database = ReadIni(INI, "MYSQL", "Database");
Port = StrToInteger(ReadIni(INI, "MYSQL", "Port"));
Socket = ReadIni(INI, "MYSQL", "Socket");
/// ClientFlag = StrToInteger(ReadIni(INI, "MYSQL", "ClientFlag"));
ClientFlag = CLIENT_MULTI_STATEMENTS;
Print ("Host: ",Host, ", User: ", User, ", Database: ",Database);
// Datenbankverbindung öffnenPrint ("Connecting...");
DB = MySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag);
if (DB == -1) { Print ("Connection failed! Error: "+MySqlErrorDescription); return; } else { Print ("Connected! DBID#",DB);}
// Ausführen der SELECT-Anweisungstring Query0,Query1,Query2,Query3,Query4,Query5,Query6,Query7;
int i,Cursor1,Cursor3,Cursor5,Cursor7,Rows,total;
int vId;
string vCode;
datetime vStartTime;
Query0 = "DROP TABLE IF EXISTS `test_table`";
MySqlExecute(DB, Query0);
Query0 = "CREATE TABLE `test_table` (id int, code varchar(50), start_date datetime)";
if (MySqlExecute(DB, Query0)) {
Print ("Table `test_table` created.");
}
else {
Print ("Table `test_table` cannot be created. Error: ", MySqlErrorDescription);
}
//--- Einfügen von Daten
Query0 = "INSERT INTO `test_table` (id, code, start_date) VALUES ("+(string)AccountNumber()+",\'ACCOUNT\',\'"+TimeToStr(TimeLocal(), TIME_DATE|TIME_SECONDS)+"\')";
if (MySqlExecute(DB, Query0)) {
Print ("Succeeded: ", Query0);
}
else {
Print ("Error: ", MySqlErrorDescription);
Print ("Query: ", Query0);
}
// mehrfach einfügen
Query0 = "INSERT INTO `test_table` (id, code, start_date) VALUES (1,\'EURUSD\',\'2014.01.01 00:00:01\');";
Query0 = Query0 + "INSERT INTO `test_table` (id, code, start_date) VALUES (2,\'EURJPY\',\'2014.01.02 00:02:00\');";
Query0 = Query0 + "INSERT INTO `test_table` (id, code, start_date) VALUES (3,\'USDJPY\',\'2014.01.03 03:00:00\');";
if (MySqlExecute(DB, Query0)) {
Print ("Succeeded! 3 rows has been inserted by one query.");
}
else {
Print ("Error of multiple statements: ", MySqlErrorDescription);
}
//--- Abfrage auswählen, benötigt Cursor ----
Query1 = "SELECT id, code, start_date FROM `test_table`";
Print ("SQL> ", Query1);
Cursor1 = MySqlCursorOpen(DB, Query1);
if (Cursor1 >= 0) {
Rows = MySqlCursorRows(Cursor1);
Print (Rows, " row(s) selected.");
for (i=0; i<Rows; i++) {
if (MySqlCursorFetchRow(Cursor1)) {
vId = MySqlGetFieldAsInt(Cursor1, 0); // id
vCode = MySqlGetFieldAsString(Cursor1, 1); // code
vStartTime = MySqlGetFieldAsDatetime(Cursor1, 2); // start_timePrint ("ROW[",i,"]: id = ", vId, ", code = ", vCode, ", start_time = ", TimeToStr(vStartTime, TIME_DATE|TIME_SECONDS));
}
total += vId;
}
//--- Daten auf der Grundlage einer Abfrage einfügen
Query2 = "INSERT INTO `test_table` (id, code, start_date) VALUES ("+(string)total+",\'ABCDEF\',\'"+TimeToStr(TimeLocal(), TIME_DATE|TIME_SECONDS)+"\'); ";
if (MySqlExecute(DB, Query2)) {
Print ("Succeeded! 1 new row has been inserted.");
}
else {
Print ("Error inserting data based on SELECT query : ", MySqlErrorDescription);
}
//---
MySqlCursorClose(Cursor1); // VERGESSEN SIE NIE, DEN CURSOR ZU SCHLIESSEN !!!
}
else {
Print ("Cursor1 opening failed. Error: ", MySqlErrorDescription);
}
//--- neuer Cursor für select ---
Query3 = "SELECT id, code, start_date FROM `test_table`";
Print ("SQL> ", Query3);
Cursor3 = MySqlCursorOpen(DB, Query3);
if (Cursor3 >= 0) {
Rows = MySqlCursorRows(Cursor3);
Print (Rows, " row(s) selected.");
for (i=0; i<Rows; i++) {
if (MySqlCursorFetchRow(Cursor3)) {
vId = MySqlGetFieldAsInt(Cursor3, 0); // id
vCode = MySqlGetFieldAsString(Cursor3, 1); // code
vStartTime = MySqlGetFieldAsDatetime(Cursor3, 2); // start_timePrint ("ROW[",i,"]: id = ", vId, ", code = ", vCode, ", start_time = ", TimeToStr(vStartTime, TIME_DATE|TIME_SECONDS));
}
}
//--- Daten aktualisieren ----
Query4 = "UPDATE `test_table` SET id=8,code='PQRXYZ',start_date=\'"+TimeToStr(TimeLocal(), TIME_DATE|TIME_SECONDS)+"\' WHERE code='ABCDEF'; ";
if (MySqlExecute(DB, Query4)) {
Print ("Succeeded! last row has been updated (code ABCDEF => PQRXYZ & new id=8.");
}
else {
Print ("Error updating data of last row : ", MySqlErrorDescription);
}
//---
MySqlCursorClose(Cursor3); // VERGESSEN SIE NIE, DEN CURSOR ZU SCHLIESSEN !!!
}
else {
Print ("Cursor3 opening failed. Error: ", MySqlErrorDescription);
}
//--- Ergebnis nach Aktualisierung anzeigen, neuer Cursor wird benötigt ----
Query5 = "SELECT id, code, start_date FROM `test_table`";
Print ("SQL> ", Query5);
Cursor5 = MySqlCursorOpen(DB, Query5);
if (Cursor5 >= 0) {
Rows = MySqlCursorRows(Cursor5);
Print (Rows, " row(s) selected.");
for (i=0; i<Rows; i++) {
if (MySqlCursorFetchRow(Cursor5)) {
vId = MySqlGetFieldAsInt(Cursor5, 0); // id
vCode = MySqlGetFieldAsString(Cursor5, 1); // code
vStartTime = MySqlGetFieldAsDatetime(Cursor5, 2); // start_timePrint ("ROW[",i,"]: id = ", vId, ", code = ", vCode, ", start_time = ", TimeToStr(vStartTime, TIME_DATE|TIME_SECONDS));
}
}
//--- Abfrage löschen ---
Query6 = "DELETE FROM `test_table` WHERE id=3; ";
if (MySqlExecute(DB, Query6)) {
Print ("Succeeded! 1 row (id=3) has been deleted.");
}
else {
Print ("Error deleting 1 row : ", MySqlErrorDescription);
}
//---
MySqlCursorClose(Cursor5); // VERGESSEN SIE NIE, DEN CURSOR ZU SCHLIESSEN !!!
}
else {
Print ("Cursor3 opening failed. Error: ", MySqlErrorDescription);
}
//--- Ergebnis nach dem Löschen anzeigen, ein weiterer Cursor wird benötigt ---
Query7 = "SELECT id, code, start_date FROM `test_table`";
Print ("SQL> ", Query7);
Cursor7 = MySqlCursorOpen(DB, Query7);
if (Cursor7 >= 0) {
Rows = MySqlCursorRows(Cursor7);
Print (Rows, " row(s) selected.");
for (i=0; i<Rows; i++) {
if (MySqlCursorFetchRow(Cursor7)) {
vId = MySqlGetFieldAsInt(Cursor7, 0); // id
vCode = MySqlGetFieldAsString(Cursor7, 1); // code
vStartTime = MySqlGetFieldAsDatetime(Cursor7, 2); // start_timePrint ("ROW[",i,"]: id = ", vId, ", code = ", vCode, ", start_time = ", TimeToStr(vStartTime, TIME_DATE|TIME_SECONDS));
}
}
//---
MySqlCursorClose(Cursor7); // VERGESSEN SIE NIE, DEN CURSOR ZU SCHLIESSEN !!!
}
else {
Print ("Cursor3 opening failed. Error: ", MySqlErrorDescription);
}
//----- am Ende ----
MySqlDisconnect(DB);
Print ("Disconnected. Script done!");
}
//+------------------------------------------------------------------+
Ihre Codes helfen mir so sehr, ich kann so viel Zeit sparen. Ich habe versucht, INSERT, SELECT, UPDATE und DELETE Abfrage erfolgreich zu tun. Wenn ich nicht falsch liege, wird der "Cursor" nur für SELECT-Abfragen benötigt ??
= pedma
Ganz genau, Mann!
Die Cursor werden nur für die Datenauswahl verwendet, da wir die Daten von der Datenbank in die MQL-Variable erhalten müssen, nicht nur um den SQL-Befehl an die Datenbank zu senden.
Ich habe mich gefragt, ob du immer noch bezahlte Entwicklungsprojekte durchführst, da ich einen Remote Trade Copier erstellen möchte, der in einen EA integriert ist, den ich verkaufen werde?
Ich habe auf Upwork nachgesehen und du scheinst in letzter Zeit keine Freelancer-Projekte abgeschlossen zu haben.
Ich habe es selbst mit der von Ihnen erstellten Bibliothek versucht, aber es hat nicht so gut geklappt. Aber ich bin mir sicher, dass es für jemanden mit Ihren Programmierfähigkeiten ein Leichtes wäre!
Ich habe mich gefragt, ob du immer noch bezahlte Entwicklungsprojekte durchführst, da ich einen Remote Trade Copier erstellen möchte, der in einen EA integriert ist, den ich verkaufen werde?
Ich habe auf Upwork nachgesehen und du scheinst in letzter Zeit keine Freelancer-Projekte abgeschlossen zu haben.
Ich habe es selbst mit der von Ihnen erstellten Bibliothek versucht, aber es hat nicht so gut geklappt. Aber ich bin mir sicher, dass es für jemanden mit Ihren Programmierfähigkeiten ein Leichtes wäre!
Vielen Dank im Voraus,
James
Hallo James,
ich arbeite bei Upwork derzeit nur an einem großen Projekt. Daher habe ich derzeit nicht viel freie Zeit. Was ist das Problem, das du mit Libs hast? Wie kann ich dir helfen?
Ok, ich sehe, Sie haben einen Expertenberater für diese Zwecke geschrieben, und es ist ohne Empfehlungen geschrieben, die ich in Artikel gepostet habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich sieht es so aus.
Ok, ich sehe, dass Sie einen Expert Advisor für diesen Zweck geschrieben haben, und er ist ohne die Empfehlungen geschrieben, die ich in meinem Artikel geschrieben habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich wird es so aussehen.
Ok, ich sehe, dass Sie einen Expert Advisor für diesen Zweck geschrieben haben, und er ist ohne die Empfehlungen geschrieben, die ich in meinem Artikel geschrieben habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich wird es so aussehen.
Ich änderte Schritt für Schritt, aber das Problem ist immer noch vorhanden, wenn der Experte in einem mt4 für vier oder mehr Symbole verwenden. es drucken " Access violation lesen 0x0000000B in '... .MQLMySQL.dll'
"
Der Code ist wie folgt
<--
#include <MQLMySQL.mqh
int MySqlErrorNumber; // aktuelle MySQL-Fehlernummer
string MySqlErrorDescription; // Fehlerbeschreibung
//+------------------------------------------------------------------+
//| Experteninitialisierungsfunktion & nbsp; |
//+------------------------------------------------------------------+
int OnInit()
OnInit(); int OnInit()
EventSetTimer(timeSeconds);
DB = MySqlConnect(Host, Benutzer, Passwort, Datenbank, Port, Socket, ClientFlag); if( DB == -1 )
if( DB == -1 )
{
Print("Datenbank ist nicht verbunden ..."); if( DB == -1 ) { print("Datenbank ist nicht verbunden ... "); }
}
return(INIT_SUCCEEDED); }
}
//+------------------------------------------------------------------+
//| Experten-Deinitialisierungsfunktion |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
MySqlDisconnect(DB);
EventKillTimer();
ObjectsDeleteAll();
}
void OnTimer()
{
//Alert(TimeCurrent());
OnTick();
}
//+------------------------------------------------------------------+
//| Experten-Tick-Funktion & nbsp; |
//+------------------------------------------------------------------+
void OnTick()
{
if( DB == -1 )
{
Alert("Datenbank ist nicht verbunden ... "); return; { Alert("Datenbank ist nicht verbunden ...")
return; }
}
if( IsExpertEnabled() && IsConnected() && AccountNumber() > 0 && DB ! = -1 )
{
int Konto = KontoNummer();
string symbol = Symbol(); if( cmd !
if( cmd ! = "" && cmd ! = NULL )
{
Symbol = cmd; }
}
symbolOrder = symbol + "_table";
double spread = (Ask - Bid); } symbolOrder = symbol + "_table"; }
admission = spread*MathPow(10, Digits).
//int DB = cMySqlConnect(Host, Benutzer, Passwort, Datenbank, Port, Socket, ClientFlag);
Query = "SELECT * FROM " + symbol + " where AccountNumber = " + (string)AccountNumber();
//Drucken(Abfrage);
int Cursor1 = MySqlCursorOpen(DB, Query);
if (Cursor1 >= 0)
{
int Rows1 = MySqlCursorRows(Cursor1); int Cursor1 = MySqlCursorOpen(DB, Query); if (Cursor1 >= 0)
int dataRows1 = Rows1;
//Alert(dataRows);
if( dataRows1 > 0 )
{
Query = "update " + symbol + " set Bid = " + (string)Bid + ", Ask = " + ( String)Ask
+ ", Spread = " + DoubleToStr(Spread, Digits)
+ ", Zeit = '" + TimeToString(TimeLocal(), TIME_DATE|TIME_SECONDS ) + "' where AccountNumber = "
+ (string)Konto; // + "' und Symbol = '" + symbol + "'".
MySqlExecute(DB, Query);
MySqlCursorClose(Cursor1);
}
else if( dataRows1 == 0 )
{
Query = "CREATE TABLE IF NOT EXISTS " + symbol + " (id int NOT NULL AUTO_ INCREMENT PRIMARY KEY, AccountNumber int, "
+ "Symbol char(20), Bid double, Ask double, Spread double,"
+ "Memo char(50), "
+ "Zeit datetime) ENGINE=MEMORY DEFAULT CHARSET=utf8 ";
MySqlExecute(DB, Query);
Query = "INSERT INTO " + symbol + "(AccountNumber, Symbol, Bid, Ask, Spread. Memo, Zeit) VALUES ("
+ (string)account + ", '" + symbol + "', "+(string)Bid+", "+ (string)Ask + ", "
+ DoubleToStr(spread, Ziffern)
+ ", '" + (string)Kontofirma()
+ "', \'"+TimeToString(TimeLocal(), TIME_DATE|TIME_SECONDS)+"\')"";
if(MySqlExecute(DB, Query) ! = true )
{
//Query = "DROP TABLE IF EXISTS `data_table`";
//MySqlExecute(DB, Query);
Query = "CREATE TABLE IF NOT EXISTS " + symbol + "(id int NOT NULL AUTO_INCREMENT PRIMARY KEY, AccountNumber int, "
+ "Symbol char(20), Bid double, Ask double, Spread double,"
+ "Memo char(50), "
+ "Zeit datetime) ENGINE=MEMORY DEFAULT CHARSET= utf8 ";
MySqlExecute(DB, Query);
}
}
MySqlCursorClose(Cursor1); // NIEMALS VERGESSEN, den CURSOR zu schließen !!!!
}
}
}
-->
Ok, ich sehe, dass Sie einen Expert Advisor für diesen Zweck geschrieben haben, und er ist ohne die Empfehlungen geschrieben, die ich in meinem Artikel geschrieben habe.
Also, gehen wir Schritt für Schritt vor: 1.
1. der Aufruf von " DB = cMySqlConnect(Host, User, Password, Database, Port, Socket, ClientFlag); " sollte innerhalb von OnInit() gemacht werden Standardfunktion anstelle von OnTick() erfolgen. 2.
2. Sie verwenden cMySqlConnect - es ist eine importierte Funktion aus der DLL, Sie müssen die Funktion MySqlConnect anstelle von cMySqlConnect-Funktion verwenden !
3) Sie müssen die Funktion MySqlDisconnect innerhalb der Standardfunktion OnDeinit() aufrufen.
4) Sie müssen die Kennung der Datenbankverbindung in der OnTick()-Standardfunktion überprüfen, um sicher zu sein, dass die Verbindung erfolgreich war.
Schließlich wird es so aussehen.
Das Problem ist, dass es nicht in einem mt4 für mehr als zwei Symbole verwendet werden kann, wenn es nur in einem Symbol verwendet wird, ist es normal. Wenn es in vier oder mehr Symbolen verwendet wird, läuft es gut, aber nach ein paar Minuten, druckt es das Problem "OnTick()". Minuten wird das Problem "Access violation read to 0x0000000B in '...MQLMySQL.db'" gedruckt. .MQLMySQL.dll'"
Die exambles ist alle Skripte, es ist nur ein Mal ausgeführt, Sie können versuchen, ein Experten rufen Sie die dll in vier oder mehr Symbole in ein oder zwei mt4, Sie können das Problem finden.
Wäre die dll braucht ein memeoy Release oder garbe Sammlung?
CRT Lecks nach der Zerstörung st atischer Daten entsorgt, und dies führt zu ο falschen Leckberichten für Objekte, die Speicher zugewiesen haben, bevor MFC initialisiert wurde, und die daher nach MFC zerstört werden nbsp;
falsche Leckmeldungen für Objekte, die Speicher zugewiesen haben, bevor die MFC
initialisiert wurde, und die daher nach dem Beenden der MFC zerstört werden. Dies wird
häufig beobachtet, wenn die MFC-DLL in einem Programm verwendet wird, das auch
die C++-Laufzeit-DLLverwendet .
Hallo noch einmal.
Anhand des Codes, den Sie uns zur Verfügung gestellt haben, vermute ich, dass Sie neu in MQL sind.
Es tut mir leid, ich habe keine Zeit, Sie zu unterrichten, aber ich habe Zeit, die Software zu testen, die ich entwickelt habe.
Es tut mir leid, dass ich keine Zeit habe, Ihnen etwas beizubringen, aber ich habe Zeit, die Software zu testen, die ich entwickelt habe.
Ich habe einen Test-EA für Sie gebaut, der auf Ihrer Logik basiert: jede Tabelle ist für jedes Währungspaar definiert und kann die Online-Marktdaten für verschiedene Konten halten.
Sie können die Logs einsehen, kein einziger Fehler "Access violation..." wurde ausgelöst. Sie können die Protokolle einsehen, kein einziger Fehler "Access violation..." wurde ausgelöst.
Das Problem liegt nicht in der MQLMySQL-Bibliothek.
EA testen.
Das ist die richtige Logik bei der Verwendung der Bibliothek.
Aufgrund der Optimierung können Sie sogar keine SELECT-Anweisung verwenden, sondern nur eine UPDATE-Anweisung ausführen und dann prüfen, ob (MySqlRowsAffected()==0) bedeutet, dass keine Zeile aktualisiert wurde. Sie haben ~100% der Aktualisierungen, also wenden Sie die INSERT-Anweisung an.
Sie haben ~100% der Aktualisierungen, also kann dieser Workaround die Leistung erhöhen und den Netzwerkverkehr reduzieren.
Und am Ende, vollständige Quellcodes des Projekts (einschließlich DLL-Entwicklung) wurde an den Artikel angehängt, können Sie es auf Ihre eigene Weise zu ändern.
Wenn Sie das Problem ohnehin in der MqlMySQL.DLL finden, können Sie es selbst debuggen und beheben.
Beste Wünsche, Eugene
Eugene
Großartige Arbeit, vielen Dank , Eugeniy.
Ihre Codes helfen mir so sehr, ich kann so viel Zeit sparen. Ich habe versucht, INSERT, SELECT, UPDATE und DELETE Abfrage erfolgreich zu tun. Wenn ich nicht falsch liege, wird der "Cursor" nur für SELECT-Abfragen benötigt ??
= pedma
Großartige Arbeit, vielen Dank , Eugeniy.
Ihre Codes helfen mir so sehr, ich kann so viel Zeit sparen. Ich habe versucht, INSERT, SELECT, UPDATE und DELETE Abfrage erfolgreich zu tun. Wenn ich nicht falsch liege, wird der "Cursor" nur für SELECT-Abfragen benötigt ??
= pedma
Ganz genau, Mann!
Die Cursor werden nur für die Datenauswahl verwendet, da wir die Daten von der Datenbank in die MQL-Variable erhalten müssen, nicht nur um den SQL-Befehl an die Datenbank zu senden.
Ich bin froh, dass meine Lösung Ihnen hilft.
Viel Glück!
Eugene
Hallo Eugene,
Ich habe mich gefragt, ob du immer noch bezahlte Entwicklungsprojekte durchführst, da ich einen Remote Trade Copier erstellen möchte, der in einen EA integriert ist, den ich verkaufen werde?
Ich habe auf Upwork nachgesehen und du scheinst in letzter Zeit keine Freelancer-Projekte abgeschlossen zu haben.
Ich habe es selbst mit der von Ihnen erstellten Bibliothek versucht, aber es hat nicht so gut geklappt. Aber ich bin mir sicher, dass es für jemanden mit Ihren Programmierfähigkeiten ein Leichtes wäre!
Vielen Dank im Voraus,
James
Hallo Eugene,
Ich habe mich gefragt, ob du immer noch bezahlte Entwicklungsprojekte durchführst, da ich einen Remote Trade Copier erstellen möchte, der in einen EA integriert ist, den ich verkaufen werde?
Ich habe auf Upwork nachgesehen und du scheinst in letzter Zeit keine Freelancer-Projekte abgeschlossen zu haben.
Ich habe es selbst mit der von Ihnen erstellten Bibliothek versucht, aber es hat nicht so gut geklappt. Aber ich bin mir sicher, dass es für jemanden mit Ihren Programmierfähigkeiten ein Leichtes wäre!
Vielen Dank im Voraus,
James
Hallo James,
ich arbeite bei Upwork derzeit nur an einem großen Projekt. Daher habe ich derzeit nicht viel freie Zeit. Was ist das Problem, das du mit Libs hast? Wie kann ich dir helfen?