Обсуждение статьи "Основы программирования на MQL5 - Строки" - страница 2

 
denkir:

...Лично мне был интересен вопрос про ограничения по длине строки...

Сейчас поэкспериментировал, 32 мб влезло, влезло бы и больше, только долго.
 

Добавляет разделитель групп разрядов в строку:

//+------------------------------------------------------------------+
//|                                        DelimiterGroupsDigits.mq5 |
//|                        Copyright 2018, MetaQuotes Software Corp. |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property script_show_inputs
//--- Внешние параметры
input double Value     =1000000;
input string Delimiter =" "; // Delimiter, by default: " ", example: 1 000 000.0
//+------------------------------------------------------------------+
//| Script program start function                                    |
//+------------------------------------------------------------------+
void OnStart(void)
  {
   ::Print(DelimiterGroupsDigits(string(Value),Delimiter));
  }
//+------------------------------------------------------------------+
//| Разделитель групп разрядов                                       |
//+------------------------------------------------------------------+
string DelimiterGroupsDigits(const string value,const string delimiter=" ")
  {
   string res=value;
   string elements[];
//--- Убираем лишние символы по краям
   ::StringTrimLeft(res);
   ::StringTrimRight(res);
//--- Проверка на вещественное число
   ushort sep   =::StringGetCharacter(".",0);
   int    total =::StringSplit(res,sep,elements);
//--- Получили строку
   if(total>0)
     {
      string str[];
      int length=::StringLen(elements[0]);
      for(int k=0,i=length-1; i>=0; i--)
        {
         int size=::ArraySize(str);
         ::ArrayResize(str,size+1);
         str[size]=::StringSubstr(elements[0],i,1);
         k++;
         //--- Добавляем разделитель
         if(k>=3 && i>0)
           {
            int array_size=::ArraySize(str);
            ::ArrayResize(str,array_size+1);
            str[array_size]=delimiter;
            k=0;
           }
        }
      //--- Собираем строку
      res="";
      int elements_total=::ArraySize(str);
      for(int i=elements_total-1; i>=0; i--)
         ::StringAdd(res,str[i]);
      //--- Если вещественное число
      if(total>1)
         ::StringAdd(res,"."+elements[1]);
     }
//--- Возвращаем результат
   return(res);
  }
//+------------------------------------------------------------------+

//---

Результат:

1 000 000.0
10,000,000.0
100'000'000.0
10 000.545
 
Anatoli Kazharski:

Добавляет разделитель групп разрядов в строку:

Как-то сложно.
 
fxsaber:
Как-то сложно.
Попробуете оптимизировать?
 
Anatoli Kazharski:
Попробуете оптимизировать?
string ModToString( ulong &Num, const int Mod = 1000, const int Len = 3 )
{
  const string Res = ((bool)(Num / Mod) ? IntegerToString(Num % Mod, Len, '0') : (string)(Num % Mod));
  
  Num /= Mod;
  
  return(Res);
}

string NumToString( ulong Num, const string Delimeter = " " )
{
  string Res = ModToString(Num);

  while (Num)
    Res = ModToString(Num) + Delimeter + Res;

  return(Res);
}

string NumToString( double Num, const int digits = 8, const string Delimeter = NULL )
{
  const string PostFix = (Num < 0) ? "-" : NULL;
  
  Num = MathAbs(Num);
    
  return(PostFix + NumToString((ulong)Num, Delimeter) + StringSubstr(DoubleToString(Num - (long)Num, digits), 1));
}

void OnStart()
{
  Print(NumToString(1234567.89, 2, " "));
}
 
fxsaber:

Отлично! И в четыре раза быстрее:

void OnStart(void)
  {
   long count=10000000;
   uint start=GetTickCount();
   for(int i=0; i<count && !IsStopped(); i++)
      DelimiterGroupsDigits(string(Value),Delimiter);

   uint end=GetTickCount()-start;
   Print("01 > ms: ",end,"; res: ",DelimiterGroupsDigits(string(Value),Delimiter));
//---
   start=GetTickCount();
   for(int i=0; i<count && !IsStopped(); i++)
      NumToString(Value,2,Delimiter);

   end=GetTickCount()-start;
   Print("02 > ms: ",end,"; res: ",NumToString(Value,2,Delimiter));
  }

//---

2018.01.30 21:02:15.996 01 > ms: 19047; res: 1 000 000.0
2018.01.30 21:02:20.683 02 > ms: 4688; res: 1 000 000.00