绕过MQL4和MQL5中的Digits(),获取任何数字的小数位数(不仅仅是引号)。 - 页 14 1...78910111213141516171819202122 新评论 fxsaber 2018.12.07 14:12 #131 我可以集思广益,研究如何快速实现将一个结构数组(长度为sizeof(int)的倍数)转换为int[]数组并从该数组中转换 出来? 实际应用是通过资源快速交换数据。我的变体 太普遍了,所以速度变慢了。 这些功能出现在MT5中 StructToCharArray CharArrayToStruct 它们在MT4中不存在,可能也不会存在。所以我们必须在有和没有这些功能的情况下解决问题(如果它们是有用的)。 这个结果将对这里的大量论坛用户有用。 我写了一个非常简单的模板,用于头脑风暴,其中有我对这个问题的解决方案。 // Решения задачи: https://www.mql5.com/ru/forum/287618/page14#comment_9806429 #define BENCH(A) \ { \ const ulong StartTime = GetMicrosecondCount(); \ A; \ Print("Time[" + #A + "] = " + (string)(GetMicrosecondCount() - StartTime)); \ } // Инициализация исходных данных int InitData( MqlTick &Ticks[], const int Amount = 1 e6, const double Price = 1.2345) { const int Size = ArrayResize(Ticks, Amount); for (int i = 0; i < Size; i++) Ticks[i].bid = Price; return(Size); } MqlTick TicksIn[]; // Массив с исходными данными. const int Init = InitData(TicksIn); // Инициализировали его. // Проверка, что два массива совпадают. bool IsCompare( const MqlTick &Ticks1[], const MqlTick &Ticks2[] ) { const int Size = ArraySize(Ticks1); bool Res = (Size == ArraySize(Ticks2)); for (int i = 0; (i < Size) && Res; i++) Res = (Ticks1[i].bid == Ticks2[i].bid); return(Res); } void OnStart() { MqlTick TicksOut[]; int Array[]; BENCH(TicksToIntArray_fxsaber1(TicksIn, Array)); // Замерили конвертацию MqlTick[] -> int[]. BENCH(IntArrayToTicks_fxsaber1(Array, TicksOut)); // Замерили конвертацию int[] -> MqlTick[]. Print(IsCompare(TicksIn, TicksOut)); // Убедились, что тики на входе и выходе совпадают. } // Варианты реализаций /***********************************************/ #include <TypeToBytes.mqh> // https://www.mql5.com/ru/code/16280 template <typename T1, typename T2> int ArrayToArray( const T1 &Source[], T2 &Target[] ) { return(_ArrayCopy(Target, Source) / sizeof(T2)); } // Перевод массива тиков в массив int[]. int TicksToIntArray_fxsaber1( const MqlTick &Ticks[], int &Array[] ) { return(ArrayToArray(Ticks, Array)); } // Перевод массива int[] в массив тиков. int IntArrayToTicks_fxsaber1( const int &Array[], MqlTick &Ticks[] ) { return(ArrayToArray(Array, Ticks)); } /***********************************************/ 结果 Time[TicksToIntArray_fxsaber1(TicksIn,Array)] = 2036468 Time[IntArrayToTicks_fxsaber1(Array,TicksOut)] = 2253915 true fxsaber 2018.12.07 15:36 #132 另一个变体template <typename T> union INTEGER { T Data; int Integer[sizeof(T) / sizeof(int)]; }; // Перевод массива тиков в массив int[]. int TicksToIntArray_fxsaber2( const MqlTick &Ticks[], int &Array[] ) { INTEGER<MqlTick> TickInteger; const int Size1 = ArraySize(Ticks); const int Size2 = ArrayResize(Array, Size1 * sizeof(MqlTick) / sizeof(int)); int j = 0; for (int i = 0; (i < Size1) && (j < Size2); i++) { TickInteger.Data = Ticks[i]; j += ArrayCopy(Array, TickInteger.Integer, j); } return(j); } // Перевод массива int[] в массив тиков. int IntArrayToTicks_fxsaber2( const int &Array[], MqlTick &Ticks[] ) { INTEGER<MqlTick> TickInteger; const int Size1 = ArraySize(Array); const int Size2 = ArrayResize(Ticks, Size1 * sizeof(int) / sizeof(MqlTick)); int j = 0; for (int i = 0; (i < Size1) && (j < Size2); j++) { i += ArrayCopy(TickInteger.Integer, Array, 0, i, sizeof(MqlTick) / sizeof(int)); Ticks[j] = TickInteger.Data; } return(j); } 结果 Time[TicksToIntArray_fxsaber2(TicksIn,Array)] = 91967 Time[IntArrayToTicks_fxsaber2(Array,TicksOut)] = 79630 true 比第二个选项快得多的东西。可能没有办法加快它的速度。 Ilya Malev 2018.12.07 17:01 #133 将一个结构数组(长度为sizeof(int)的倍数)转换为一个int[]数组的快速实现? 类似这样的事情 #property strict template< typename S, typename T > union UDT{ UDT(){for(int i=0;i<sizeof(S)/sizeof(T);i++)t[i]=0;} UDT(S&src){s=src;} UDT(T&src[],int k=0){for(int i=0;i<sizeof(S)/sizeof(T);i++)t[i]=src[i+k];} void to(S&dst){dst=s;} void to(T&dst[],int k=0){for(int i=0;i<sizeof(S)/sizeof(T);i++)dst[i+k]=t[i];} S s; T t[sizeof(S)/sizeof(T)];}; template< typename S, typename T > void StructToArray(S&src[],T&dst[]){ ArrayResize(dst,ArraySize(src)*(sizeof(S)/sizeof(T))); for(int i=0;i<ArraySize(dst)/(sizeof(S)/sizeof(T));i++){UDT<S,T>u(src[i]);u.to(dst,i*(sizeof(S)/sizeof(T)));}} template< typename S, typename T > void ArrayToStruct(T&src[],S&dst[]){ ArrayResize(dst,ArraySize(src)/(sizeof(S)/sizeof(T))); for(int i=0;i<ArraySize(dst);i++){UDT<S,T>u(src,i*(sizeof(S)/sizeof(T)));u.to(dst[i]);}} void OnStart() { MqlRates rates[],r2[]; int l[]; CopyRates(_Symbol,_Period,0,10,rates); for(int i=0;i<10;i++)printf("open=%f, high=%f, low=%f, close=%f, time=%s",rates[i].open,rates[i].high,rates[i].low,rates[i].close,TimeToStr(rates[i].time)); Print(""); StructToArray(rates,l); ArrayToStruct(l,r2); for(int i=0;i<ArraySize(r2);i++)printf("open=%f, high=%f, low=%f, close=%f, time=%s",r2[i].open,r2[i].high,r2[i].low,r2[i].close,TimeToStr(r2[i].time)); } fxsaber 2018.12.07 18:31 #134 Ilya Malev:类似这样的事情。 https://www.mql5.com/ru/forum/287618/page14#comment_9807465 TicksToIntArray_fxsaber2 Time[TicksToIntArray(TicksIn,Array)] = 735252 IntArrayToTicks_fxsaber2 Time[IntArrayToTicks(Array,TicksOut)] = 591458 true https://www.mql5.com/ru/forum/287618/page14#comment_9808274 TicksToIntArray_antfx1 Time[TicksToIntArray(TicksIn,Array)] = 398796 IntArrayToTicks_antfx1 Time[IntArrayToTicks(Array,TicksOut)] = 296646 true干得好!我将进入代码,谢谢。 听起来ArrayCopy 是一个真正的慢郎中。 ZY从运行到运行,我得到非常不同的结果。例如,如果我改变测试的顺序,一切几乎都会被颠覆。显然,我需要一个更客观的速度测量。 附加的文件: StructToArray.mq5 6 kb Ilya Malev 2018.12.07 18:42 #135 在没有多加思考和调试的情况下,我写了第一个想到的东西,所以可能会有很多小毛病。我自己以前没有遇到过这样的任务(尽管我曾广泛地与工会合作)。 Ilya Malev 2018.12.07 18:51 #136 fxsaber:ZZZ,ArrayCopy似乎有点拖沓。我记得在一些本地任务中进行测量,我必须复制少量的元素。在16个元素以下,for循环比ArrayCopy 快得多,当元素数更多时,ArrayCopy更快。当然,最快的变体是完全没有循环的(就像我在上一页的函数)。 fxsaber 2018.12.07 19:12 #137 Ilya Malev:最快的方法是完全不用循环(就像我在前一页的函数)。我不明白。 Ilya Malev 2018.12.07 19:53 #138 fxsaber:我不明白。我的观点是,for(int i=0; i<5; i++) dst[i]=src[i]; 比dst[0]=src[0];dst[1]=src[1];dst[2]=src[2];dst[3]=src[3];dst[4]=src[4] 工作得慢。 考虑到与循环管理有关的额外操作,这一点非常明显) 而CopyArray的工作速度比它们都快得多,因为我现在检查了。也许这取决于情况,当然。 Ilya Malev 2018.12.07 20:12 #139 是的,这将工作得更 快(在可能的情况下,用ArrayCopy 代替,其余的都一样)。 template< typename S, typename T > union UTS2{ UTS2(){for(int i=0;i<sizeof(S)/sizeof(T);i++)t[i]=0;} UTS2(S&src){s=src;} UTS2(T&src[],int k=0){ArrayCopy(t,src,0,k,sizeof(S)/sizeof(T));}//for(int i=0;i<sizeof(S)/sizeof(T);i++)t[i]=src[i+k];} void to(S&dst){dst=s;} void to(T&dst[],int k=0){ArrayCopy(dst,t,k,0,sizeof(S)/sizeof(T));}//for(int i=0;i<sizeof(S)/sizeof(T);i++)dst[i+k]=t[i];} S s; T t[sizeof(S)/sizeof(T)];}; template< typename S, typename T > void StructToArray2(S&src[],T&dst[]){ ArrayResize(dst,ArraySize(src)*(sizeof(S)/sizeof(T))); for(int i=0;i<ArraySize(dst)/(sizeof(S)/sizeof(T));i++){UTS2<S,T>u(src[i]);u.to(dst,i*(sizeof(S)/sizeof(T)));}} template< typename S, typename T > void ArrayToStruct2(T&src[],S&dst[]){ ArrayResize(dst,ArraySize(src)/(sizeof(S)/sizeof(T))); for(int i=0;i<ArraySize(dst);i++){UTS2<S,T>u(src,i*(sizeof(S)/sizeof(T)));u.to(dst[i]);}} 我告诉过你,我写的是第一个想到的东西,没有测试))。 Igor Makanu 2018.12.07 20:19 #140 Ilya Malev:而CopyArray,正如我现在检查的那样,似乎比这两个选项都快得多。当然,也许这要看情况而定。如果ArrayCopy()是根据Cish memmove()的原则进行的。我认为ArrayCopy()的速度取决于内存分配的速度,如果中间缓冲区的内存已经准备好供复制,ArrayCopy()将很快被执行,如果内存没有分配,你将开始请求操作系统分配内存你可以试着测试一下--用大的数据量调用ArrayCopy(),从而为交换准备好缓冲内存,然后用ArrayCopy()做一个循环,用较小的数据量进行复制,用速度计进行测试。 1...78910111213141516171819202122 新评论 您错过了交易机会: 免费交易应用程序 8,000+信号可供复制 探索金融市场的经济新闻 注册 登录 拉丁字符(不带空格) 密码将被发送至该邮箱 发生错误 使用 Google 登录 您同意网站政策和使用条款 如果您没有帐号,请注册 可以使用cookies登录MQL5.com网站。 请在您的浏览器中启用必要的设置,否则您将无法登录。 忘记您的登录名/密码? 使用 Google 登录
我可以集思广益,研究如何快速实现将一个结构数组(长度为sizeof(int)的倍数)转换为int[]数组并从该数组中转换 出来?
实际应用是通过资源快速交换数据。我的变体 太普遍了,所以速度变慢了。
这些功能出现在MT5中
它们在MT4中不存在,可能也不会存在。所以我们必须在有和没有这些功能的情况下解决问题(如果它们是有用的)。
这个结果将对这里的大量论坛用户有用。
我写了一个非常简单的模板,用于头脑风暴,其中有我对这个问题的解决方案。
结果
结果
比第二个选项快得多的东西。可能没有办法加快它的速度。
将一个结构数组(长度为sizeof(int)的倍数)转换为一个int[]数组的快速实现?
类似这样的事情
类似这样的事情。
干得好!我将进入代码,谢谢。
听起来ArrayCopy 是一个真正的慢郎中。
ZY从运行到运行,我得到非常不同的结果。例如,如果我改变测试的顺序,一切几乎都会被颠覆。显然,我需要一个更客观的速度测量。
ZZZ,ArrayCopy似乎有点拖沓。
我记得在一些本地任务中进行测量,我必须复制少量的元素。在16个元素以下,for循环比ArrayCopy 快得多,当元素数更多时,ArrayCopy更快。当然,最快的变体是完全没有循环的(就像我在上一页的函数)。
最快的方法是完全不用循环(就像我在前一页的函数)。
我不明白。
我不明白。
我的观点是,for(int i=0; i<5; i++) dst[i]=src[i]; 比dst[0]=src[0];dst[1]=src[1];dst[2]=src[2];dst[3]=src[3];dst[4]=src[4] 工作得慢。
考虑到与循环管理有关的额外操作,这一点非常明显)
而CopyArray的工作速度比它们都快得多,因为我现在检查了。也许这取决于情况,当然。
是的,这将工作得更 快(在可能的情况下,用ArrayCopy 代替,其余的都一样)。
我告诉过你,我写的是第一个想到的东西,没有测试))。
而CopyArray,正如我现在检查的那样,似乎比这两个选项都快得多。当然,也许这要看情况而定。
如果ArrayCopy()是根据Cish memmove()的原则进行的。
我认为ArrayCopy()的速度取决于内存分配的速度,如果中间缓冲区的内存已经准备好供复制,ArrayCopy()将很快被执行,如果内存没有分配,你将开始请求操作系统分配内存
你可以试着测试一下--用大的数据量调用ArrayCopy(),从而为交换准备好缓冲内存,然后用ArrayCopy()做一个循环,用较小的数据量进行复制,用速度计进行测试。