"Apotheosis", kendisinin nasıl çalıştığını söyleyemediği fxsaber'ın bir ifadesini düşünüyorum, sadece "kod tekrar tekrar test edildi ve çalışıyor" dedi. Bana göre bu olmamalı:
Bu kod, otfFilingType siparişinin doldurulup doldurulamayacağını kontrol eder ve strSymbol sembolünde mevcutsa, aksi takdirde doğrudur.
Nasıl çalıştığını tam olarak anlayamıyorum. Ve ben sadece fxsaber'ın otoritesine güveniyorum.
Belki biri açıklar?
Anlamak için, bu hantal ifadeyi geri dönüşten bileşenlere ayrıştırmak yeterlidir.
bu arada, bu kod sadece spagetti gibi görünüyor, ancak bunun şu anda kod tabanındaki muhtemelen en faydalı yazar olduğu ve ben de onun kodlarını olduğu gibi kullandığım gerçeği göz önüne alındığında, başkasının eleştirmesine izin verin
bu arada, bu kod sadece spagetti gibi görünüyor, ancak bunun muhtemelen şu anda kod tabanındaki en yararlı yazar olduğu ve ben de onun kodlarını olduğu gibi kullandığım gerçeği göz önüne alındığında, başkasının eleştirmesine izin verin
Eleştiriden bahsetmiyorum, ne verebileceğini anlamaya çalışıyorum .... ama konuşmanın gösterdiği gibi ve @fxsaber açıkça itiraf etti - baş ağrısından başka bir şey değil
Not: Küçük canavarın orijinal versiyonunun daha görsel görünmesi kuvvetle muhtemeldir;)
Ancak bundan sonra, giderek daha fazla işlevsellik gerekliydi ve kod yavaş yavaş etle kaplandı. Doldurma işlevi ile farklıydı. Orada hiçbir şey büyümedi, hemen yazıldı.
Derleyicinin tam olarak nasıl yapacağını sadece kendisi bilir. Modern derleyicilerde yerleşik çarpıcı buluşsal yöntemler vardır. Ortalama kodlayıcıya uyum sağlarlar ve neye ihtiyacı olduğunu zaten daha iyi bilirler. Bir derleyici için yapılacak en iyi şey, kısa fonksiyonlarla basit, anlaşılır kod yazmaktır. Derleyicinin birçok düğüm fonksiyonundan oluşan kaynak kod grafiğini analiz ederek nihai programı oluşturması çok daha kolay ve verimlidir. Bu sadece performans üzerinde olumlu bir etkiye sahip olacaktır, çünkü gerekli işlevler doğru yerlerde sıralanacaktır.
Kesinlikle doğru.
MQL5 hakkında konuşursak, 10-20-30 yıl önceki "optimizasyon" yöntemlerini unutabiliriz. Mümkün olduğunca okunabilir kod yazmanız gerekir. Kalitenin ölçüsü, hacker çanları ve ıslıkları ve saf gösterişler değil, odur.
Niye ya?
Evet, çünkü derleyici 5-10 döngü kod yeniden sıralamasından geçecek, düzinelerce optimizasyon modelinin kullanımından bahsetmeden, grafiklerin sonlarını şaşırtıcı derecede net ve kısa bir şekilde gösterecektir.
MQL5 derleyicisi, insanların zil ve ıslıklarla +%2 hız yapma girişimlerini komik buluyor.
İlgilenenler için, matematiksel hesaplamalar dallar olmadan yapılır ve bir komut için (128 bit veri) aynı anda iki kök hesaplanır
Sonuçta bu bir sanat eseri. Montajcı komutunun 4 çağrısı için 8 kök hesaplanır. Bir aramada iki çift sayı hesaplandı.
Bir dizideki işlemler sırasında, çift -> tamsayı indeks dönüşümünde kontroller, dallanma ve kayıplarla her şey normal şekilde gider
Bu örnekte dizilerle çalışırken, performans üzerinde çok kötü bir etkisi olan sürekli bir FPU / ALU karışımı vardır.
Dinamik bir diziye erişimin optimizasyonu övgünün ötesinde mükemmeldir. Ancak FPU/ALU işlemlerini karıştırmak + çift çevirmek -> tamsayı + dallara ayırmak zaman kaybettirir
Genel sonuç: MQL5'teki matematik, mükemmel optimizasyon sayesinde kazanır. Kaybeden diziler değil, matematik kazanır.
Tam tersi, iki "if" ile - "veya" operatöründen çok daha kolay.
Açıkçası, önce bir koşulu izlemek ve yürütme durumunda işlevden ayrılmak ve ardından başka bir koşulu kontrol etmek ve yürütme durumunda da bırakmak daha kolaydır. Mantıksal bir "veya" ("ve" ile kolayca karıştırılabilen) aracılığıyla karmaşık bir koşulun sonucu olarak ne olduğunu anlamak ve her iki iade seçeneğini de takip etmek.
Aşağıda "bunun gerekçesinin hata ayıklama olduğunu" okumak oldukça komik, çünkü bu, bu tür kodun çok daha anlaşılır olduğu anlamına geliyor (aksi halde neden hata ayıklamada?).
"Apotheosis", kendisinin nasıl çalıştığını söyleyemediği fxsaber'ın bir ifadesini düşünüyorum, sadece "kod tekrar tekrar test edildi ve çalışıyor" dedi. Bana göre bu olmamalı:
Bu kod, otfFilingType siparişinin doldurulup doldurulamayacağını kontrol eder ve strSymbol sembolünde mevcutsa, aksi takdirde doğrudur.
Nasıl çalıştığını tam olarak anlayamıyorum. Ve ben sadece fxsaber'ın otoritesine güveniyorum.
Belki biri açıklar?
Bir keresinde oturdum ve aşamalı olarak ayırdım, bir parça kağıt ile bir kaleme ihtiyacım var gibi görünüyor)
Bu analiz neden yararlıydı - Numaralandırmaların yapısı değişirse her şeyin bozulacağını anladım) çünkü. numaralandırma değerlerinin tamsayı oranları kullanılır (ki, numaralandırma fikrine göre, sadece kapsüllenmelidir). Bundan kendim kaçınmaya çalışıyorum, maksimum ilişki az ya da çok. WinAPI ile uğraşanlar için muhtemelen tanıdık gelecektir.
MQL5 hakkında konuşursak, 10-20-30 yıl önceki "optimizasyon" yöntemlerini unutabiliriz. Mümkün olduğunca okunabilir kod yazmanız gerekir. Kalitenin ölçüsü, hacker çanları ve ıslıkları ve saf gösterişler değil, odur.
Aynen öyle. Bu sonuca uzun zaman önce vardım. Ama derleyicinin daha iyisini yapacağını düşündüğüm için değil. Ve koddaki sorunların ana kaynağı kişinin kendisi olduğu için, yani kodun mümkün olduğunca basit ve şeffaf olması için mümkünse kodu yazmanız gerekir.
Bunu "şeffaf bir şekilde" yapmanın imkansız olduğu durumlarda, neden böyle olduğu ve başka türlü değil, ayrıntılı yorumlar gereklidir.
Pekala, derleyici... bunu yeterince verimli bir şekilde yapmasa bile, programın çalışmasının bazı yönlerini hesaba katmamanız nedeniyle potansiyel bir hatadan daha az sorun teşkil eder.
Kod çok basit ve kısadır ( açıklama ). FP'ye yazarsanız, karşılaştırmak ilginç olacaktır.
Rica ederim. FP stilinde C#:
using System;
using System.Linq;
using System.Collections.Generic;
using static FeesCalculator.FeesCalcs;
using System.Text;
using static System.Math;
namespace FeesCalculator
{
publicstaticclass EnumerableExt
{
/// <summary>/// Call of function 'action' for each element if sequence (mapping)./// </summary>/// <typeparam name="T"></typeparam>/// <param name="seq">Enumerable sequence</param>/// <param name="action">Need action</param>publicstaticvoid Map<T>( this IEnumerable<T> seq, Action<T> action)
{
foreach (var item in seq)
action(item);
}
}
/// <summary>/// Инвестиционный результат/// </summary>public record AccountRecord
{
publicdouble Investor { get; init; }
publicdouble Manager { get; init; }
publicdouble Summary { get; init; }
publicstatic AccountRecord operator *(AccountRecord r, double v)
{
returnnew AccountRecord
{
Investor = r.Investor * v,
Manager = r.Manager * v,
Summary = r.Summary * v
};
}
publicoverridestring ToString()
{
StringBuilder sb = new StringBuilder();
sb.Append(nameof(Investor)).Append( " = " ).Append(Investor.ToString( "F4" )).Append( ' ' );
sb.Append(nameof(Manager)).Append( " = " ).Append(Manager.ToString( "F4" )).Append( ' ' );
sb.Append(nameof(Summary)).Append( " = " ).Append(Summary.ToString( "F4" ));
return sb.ToString();
}
}
/// <summary>/// Параметры оферты/// </summary>public record PammSet
{
/// <summary>/// Доходность за расчетный период/// </summary>publicdouble Perfomance { get; init; }
/// <summary>/// Вознаграждение управляющего/// </summary>publicdouble Gift { get; init; }
/// <summary>/// Количество расчетных периодов/// </summary>publicint N { get; init; }
/// <inheritdoc/>publicoverridestring ToString()
{
StringBuilder str = new StringBuilder();
str.Append( "Доходность за расчетный период: " ).Append((Perfomance * 100.0 ).ToString( "F1" )).Append( "%\t\n" );
str.Append( "Вознаграждение управляющего: " ).Append((Gift * 100.0 ).ToString( "F1" )).Append( "%\t\n" );
str.Append( "Количество расчетных периодов: " ).Append(N);
return str.ToString();
}
}
/// <summary>/// Формулы расчета/// </summary>publicclass FeesCalcs
{
/// <summary>/// Если управляющий снимает деньги в конце каждого расчетного периода/// </summary>/// <param name="Performance"></param>/// <param name="Gift"></param>/// <param name="N"></param>/// <returns></returns>publicstatic AccountRecord Set1(PammSet set)
{
Func< double > investor = () => Pow( 1 + (set.Perfomance) * ( 1 - set.Gift), set.N);
Func< double > manager = () => (investor() - 1 ) * set.Gift / ( 1 - set.Gift);
AccountRecord ac = new AccountRecord
{
Investor = investor(),
Manager = manager(),
Summary = investor() + manager()
};
return ac;
}
/// <summary>/// Если ничего не делалось в расчетные периоды/// </summary>/// <param name="Performance"></param>/// <param name="Gift"></param>/// <param name="N"></param>/// <returns></returns>publicstatic AccountRecord Set2(PammSet set)
{
Func< double > summary = () => Pow(set.Perfomance + 1 , set.N);
Func< double > manager = () => (summary() - 1 ) * set.Gift;
double s = summary();
double d = manager();
AccountRecord ac = new AccountRecord
{
Summary = summary(),
Manager = manager(),
Investor = summary() - manager()
};
return ac;
}
/// <summary>/// Если управляющий снимает деньги в конце каждого расчетного периода и реинвестирует их/// </summary>/// <param name="Performance"></param>/// <param name="Gift"></param>/// <param name="N"></param>/// <returns></returns>publicstatic AccountRecord Set3(PammSet set)
{
Func< double > summary = () => Pow(set.Perfomance + 1 , set.N);
Func< double > investor = () => Pow( 1 + (set.Perfomance) * ( 1 - set.Gift), set.N);
returnnew AccountRecord
{
Summary = summary(),
Investor = investor(),
Manager = summary() - investor()
};
}
/// <summary>/// Сопостовление: описание - функция расчета/// </summary>publicstatic readonly Dictionary< string , Func<PammSet, AccountRecord>> DescrToAccountRecord = new Dictionary< string , Func<PammSet, AccountRecord>>
{
{ "Если управляющий снимает деньги в конце каждого расчетного периода (1)" , Set1 },
{ "Если ничего не делалось в расчетные периоды (2)" , Set2 },
{ "Если управляющий снимает деньги в конце каждого расчетного периода и реинвестирует их (3)" , Set3 },
};
}
class Program
{
staticvoid Main( string [] args)
{
var _ = args.Select((a) => double .Parse(a)).Take( 3 ).ToList();
PammSet pamm = new PammSet
{
Perfomance = _[ 0 ]/ 100.0 ,
Gift = _[ 1 ]/ 100.0 ,
N = ( int )_[ 2 ]
};
Console.WriteLine($ "Данные для инвестиционного счета со следующими характеристиками:\n\n{pamm}\n" );
Console.WriteLine( "Конечный результат для Инвестора, Управляющего и Суммарно:\n" );
Func<KeyValuePair< string , Func<PammSet, AccountRecord>>, string > f = (kvp) => kvp.Key + ".\n" + kvp.Value(pamm).ToString() + "\n" ;
Enumerable.Select(DescrToAccountRecord, f).Map((s) => Console.WriteLine(s));
Console.WriteLine(pamm);
Func< int , PammSet> toPamm = (n) => new PammSet { Perfomance = pamm.Perfomance, Gift = pamm.Gift, N = n };
Func<PammSet, IEnumerable<AccountRecord>> toAccs = (n) => DescrToAccountRecord.Select((s) => s.Value(n));
var accounts = Enumerable.Repeat( 1 , pamm.N).Select((a, b) => a + b).Select(toPamm).Select(toAccs);
Func<AccountRecord, string > toString = (ar) => ar.Investor.ToString( "F2" ) + "\t" +
ar.Manager.ToString( "F2" ) + "\t" +
ar.Summary.ToString( "F2" ) + "\t" ;
int period = default ;
accounts.Map
(
(en) =>
{
Console.Write($ "{++period}:\t" );
en.Map((ar) =>
Console.Write(toString(ar)));
Console.WriteLine();
}
);
}
}
}
FP elbette çok çarpıktır (FP kodlayıcısı çarpık kodlayıcıyı alt FP dilinde C# yazdığı için) Ama amaç modern OOP YaP'larda bunun FP'de mümkün olduğunu göstermektir. Sınırlı tabi ki bu F# veya Haskell değil ama kimse FP tarzında yazmayı yasaklamıyor. Değişmezlik, daha yüksek dereceli işlevler, kapatmalar, eşlemeler vb. kullanın. - her şey mümkün, lütfen. Sadece bundan gelen kod bir nedenden dolayı ideal hale gelmiyor.
ps Kodun genel yapısı kasıtlı olarak orijinali taklit eder. FP'de iyi bir şekilde, karmaşık nesneler ve foreach bir Haritayı taklit etmeden tamamen farklı bir şekilde gerekli olsa da, sanatçı elinden gelenin en iyisini yaptı.
#property strict#property script_show_inputsinputdouble inPerformance = 100 ; // Сколько процентов дает система за периодinputdouble inGift = 50 ; // Награда управляющего в процентах (< 100)inputint inN = 12 ; // Сколько расчетных периодовstruct BASE
{
double Investor;
double Manager;
double Summary;
// Если управляющий снимает деньги в конце каждого расчетного периода.void Set1( constdouble Performance, constdouble Gift, constint N )
{
this .Investor = :: MathPow ( 1 + (Performance - 1 )* ( 1 - Gift), N);
this .Manager = ( this .Investor - 1 ) * Gift / ( 1 - Gift);
this .Summary = this .Investor + this .Manager;
return ;
}
// Если ничего не делалось в расчетные периоды.void Set2( constdouble Performance, constdouble Gift, constint N )
{
this .Summary = :: MathPow (Performance, N);
this .Manager = ( this .Summary - 1 ) * Gift;
this .Investor = this .Summary - this .Manager;
return ;
}
// Если управляющий снимает деньги в конце каждого расчетного периода и реинвестирует их.void Set3( constdouble Performance, constdouble Gift, constint N )
{
this .Summary = :: MathPow (Performance, N);
this .Investor = :: MathPow ( 1 + (Performance - 1 )* ( 1 - Gift), N);
this .Manager = this .Summary - this .Investor;
return ;
}
voidoperator *=( constdouble Deposit = 1 )
{
this .Investor *= Deposit;
this .Manager *= Deposit;
this .Summary *= Deposit;
return ;
}
#define TOSTRING(A) #A + " = " + :: DoubleToString (A, 4 ) + " "string ToString( constbool FlagName = true ) const
{
return (FlagName ? TOSTRING(Investor) + TOSTRING(Manager) + TOSTRING(Summary)
: :: StringFormat ( "||%-12.4f||%-12.4f||%-12.4f||" , this .Investor, this .Manager, this .Summary));
}
#undef TOSTRING
};
struct PAMM
{
double Performance; // Доходность за расчетный периодdouble Gift; // Вознагражение управляющего.int N; // Сколько расчетных периодов.
BASE Base1; // Если управляющий снимает деньги в конце каждого расчетного периода.
BASE Base2; // Если ничего не делалось в расчетные периоды.
BASE Base3; // Если управляющий снимает деньги в конце каждого расчетного периода и реинвестирует их.void Set( constdouble dPerformance, constdouble dGift, constint iN )
{
this .Performance = dPerformance;
this .Gift = dGift;
this .N = iN;
this .Base1.Set1( 1 + this .Performance / 100 , this .Gift / 100 , this .N);
this .Base2.Set2( 1 + this .Performance / 100 , this .Gift / 100 , this .N);
this .Base3.Set3( 1 + this .Performance / 100 , this .Gift / 100 , this .N);
}
voidoperator *=( constdouble Deposit = 1 )
{
this .Base1 *= Deposit;
this .Base2 *= Deposit;
this .Base3 *= Deposit;
return ;
}
string GetDescription( void ) const
{
return ( "Доходность за расчетный период " + :: DoubleToString ( this .Performance, 1 ) + "%\n" +
"Вознагражение управляющего " + :: DoubleToString ( this .Gift, 1 ) + "%\n" +
"Количество расчетных периодов. " + ( string ) this .N);
}
string ToString( constbool FlagName = true , constbool FlagDescription = true ) const
{
return (FlagDescription ? "Данные для инвестиционного счета со следующими характеристиками:\n\n" + this .GetDescription() +
"\n\nКонечный результат для Инвестора, Управляющего и Суммарно:""\n\nЕсли управляющий снимает деньги в конце каждого расчетного периода (1).\n" + this .Base1.ToString(FlagName) +
"\n\nЕсли ничего не делалось в расчетные периоды (2).\n" + this .Base2.ToString(FlagName) +
"\n\nЕсли управляющий снимает деньги в конце каждого расчетного периода и реинвестирует их (3).\n" + this .Base3.ToString(FlagName)
: this .Base1.ToString(FlagName) + this .Base2.ToString(FlagName) + this .Base3.ToString(FlagName));
}
};
voidOnStart ()
{
PAMM Pamm;
Pamm.Set(inPerformance, inGift, inN);
Print (Pamm.ToString());
string Str = Pamm.GetDescription() + "\n " ;
for ( int i = 1 ; i <= 3 ; i++ )
Str += :: StringFormat ( "||%-12s||%-12s||%-12s||" , "Investor" + ( string )i, "Manager" + ( string )i, "Summary" + ( string )i);
for ( int i = 1 ; i <= inN; i++ )
{
Pamm.Set(inPerformance, inGift, i);
Str += StringFormat ( "\n%-2d:" , i) + Pamm.ToString( false , false );
}
Print (Str);
}
Resmi olarak, bu OOP'dir. Ama en ilkel kısmı. Ancak, onsuz yaşayamazdı. Belki aptalca, beyin başka bir şeye dönüştü ve ben bunu perçinledim.
"Apotheosis", kendisinin nasıl çalıştığını söyleyemediği fxsaber'ın bir ifadesini düşünüyorum, sadece "kod tekrar tekrar test edildi ve çalışıyor" dedi. Bana göre bu olmamalı:
Bu kod, otfFilingType siparişinin doldurulup doldurulamayacağını kontrol eder ve strSymbol sembolünde mevcutsa, aksi takdirde doğrudur.
Nasıl çalıştığını tam olarak anlayamıyorum. Ve ben sadece fxsaber'ın otoritesine güveniyorum.
Belki biri açıklar?
Anlamak için, bu hantal ifadeyi geri dönüşten bileşenlere ayrıştırmak yeterlidir.
"Son, araçları haklı çıkarır" örneğiniz
bu arada, bu kod sadece spagetti gibi görünüyor, ancak bunun şu anda kod tabanındaki muhtemelen en faydalı yazar olduğu ve ben de onun kodlarını olduğu gibi kullandığım gerçeği göz önüne alındığında, başkasının eleştirmesine izin verin
bu arada, bu kod sadece spagetti gibi görünüyor, ancak bunun muhtemelen şu anda kod tabanındaki en yararlı yazar olduğu ve ben de onun kodlarını olduğu gibi kullandığım gerçeği göz önüne alındığında, başkasının eleştirmesine izin verin
Eleştiriden bahsetmiyorum, ne verebileceğini anlamaya çalışıyorum .... ama konuşmanın gösterdiği gibi ve @fxsaber açıkça itiraf etti - baş ağrısından başka bir şey değil
Not: Küçük canavarın orijinal versiyonunun daha görsel görünmesi kuvvetle muhtemeldir;)
Not: Küçük canavarın orijinal versiyonunun daha görsel görünmesi kuvvetle muhtemeldir;)
ZIP'den alınmıştır (ilk sürümü içerir).
Ancak bundan sonra, giderek daha fazla işlevsellik gerekliydi ve kod yavaş yavaş etle kaplandı. Doldurma işlevi ile farklıydı. Orada hiçbir şey büyümedi, hemen yazıldı.
Derleyicinin tam olarak nasıl yapacağını sadece kendisi bilir. Modern derleyicilerde yerleşik çarpıcı buluşsal yöntemler vardır. Ortalama kodlayıcıya uyum sağlarlar ve neye ihtiyacı olduğunu zaten daha iyi bilirler. Bir derleyici için yapılacak en iyi şey, kısa fonksiyonlarla basit, anlaşılır kod yazmaktır. Derleyicinin birçok düğüm fonksiyonundan oluşan kaynak kod grafiğini analiz ederek nihai programı oluşturması çok daha kolay ve verimlidir. Bu sadece performans üzerinde olumlu bir etkiye sahip olacaktır, çünkü gerekli işlevler doğru yerlerde sıralanacaktır.
Kesinlikle doğru.
MQL5 hakkında konuşursak, 10-20-30 yıl önceki "optimizasyon" yöntemlerini unutabiliriz. Mümkün olduğunca okunabilir kod yazmanız gerekir. Kalitenin ölçüsü, hacker çanları ve ıslıkları ve saf gösterişler değil, odur.
Niye ya?
Evet, çünkü derleyici 5-10 döngü kod yeniden sıralamasından geçecek, düzinelerce optimizasyon modelinin kullanımından bahsetmeden, grafiklerin sonlarını şaşırtıcı derecede net ve kısa bir şekilde gösterecektir.
MQL5 derleyicisi, insanların zil ve ıslıklarla +%2 hız yapma girişimlerini komik buluyor.
Sonuçta bu bir sanat eseri. Montajcı komutunun 4 çağrısı için 8 kök hesaplanır. Bir aramada iki çift sayı hesaplandı.İlgilenenler için, matematiksel hesaplamalar dallar olmadan yapılır ve bir komut için (128 bit veri) aynı anda iki kök hesaplanır
Bu kod, aşağıdaki montajcı SSE koduna dönüşür:
Genel sonuç: MQL5'teki matematik, mükemmel optimizasyon sayesinde kazanır. Kaybeden diziler değil, matematik kazanır.
Nedenmiş ?
Tam tersi, iki "if" ile - "veya" operatöründen çok daha kolay.
Açıkçası, önce bir koşulu izlemek ve yürütme durumunda işlevden ayrılmak ve ardından başka bir koşulu kontrol etmek ve yürütme durumunda da bırakmak daha kolaydır. Mantıksal bir "veya" ("ve" ile kolayca karıştırılabilen) aracılığıyla karmaşık bir koşulun sonucu olarak ne olduğunu anlamak ve her iki iade seçeneğini de takip etmek.
Aşağıda "bunun gerekçesinin hata ayıklama olduğunu" okumak oldukça komik, çünkü bu, bu tür kodun çok daha anlaşılır olduğu anlamına geliyor (aksi halde neden hata ayıklamada?).
"Apotheosis", kendisinin nasıl çalıştığını söyleyemediği fxsaber'ın bir ifadesini düşünüyorum, sadece "kod tekrar tekrar test edildi ve çalışıyor" dedi. Bana göre bu olmamalı:
Bu kod, otfFilingType siparişinin doldurulup doldurulamayacağını kontrol eder ve strSymbol sembolünde mevcutsa, aksi takdirde doğrudur.
Nasıl çalıştığını tam olarak anlayamıyorum. Ve ben sadece fxsaber'ın otoritesine güveniyorum.
Belki biri açıklar?
Bir keresinde oturdum ve aşamalı olarak ayırdım, bir parça kağıt ile bir kaleme ihtiyacım var gibi görünüyor)
Bu analiz neden yararlıydı - Numaralandırmaların yapısı değişirse her şeyin bozulacağını anladım) çünkü. numaralandırma değerlerinin tamsayı oranları kullanılır (ki, numaralandırma fikrine göre, sadece kapsüllenmelidir). Bundan kendim kaçınmaya çalışıyorum, maksimum ilişki az ya da çok. WinAPI ile uğraşanlar için muhtemelen tanıdık gelecektir.
Anlamak için, bu hantal ifadeyi geri dönüşten bileşenlere ayrıştırmak yeterlidir.
Evet, denedim. Ancak, sökmek için yeterli motivasyon yoktu ...
Kesinlikle doğru.
MQL5 hakkında konuşursak, 10-20-30 yıl önceki "optimizasyon" yöntemlerini unutabiliriz. Mümkün olduğunca okunabilir kod yazmanız gerekir. Kalitenin ölçüsü, hacker çanları ve ıslıkları ve saf gösterişler değil, odur.
Aynen öyle. Bu sonuca uzun zaman önce vardım. Ama derleyicinin daha iyisini yapacağını düşündüğüm için değil. Ve koddaki sorunların ana kaynağı kişinin kendisi olduğu için, yani kodun mümkün olduğunca basit ve şeffaf olması için mümkünse kodu yazmanız gerekir.
Bunu "şeffaf bir şekilde" yapmanın imkansız olduğu durumlarda, neden böyle olduğu ve başka türlü değil, ayrıntılı yorumlar gereklidir.
Pekala, derleyici... bunu yeterince verimli bir şekilde yapmasa bile, programın çalışmasının bazı yönlerini hesaba katmamanız nedeniyle potansiyel bir hatadan daha az sorun teşkil eder.
Kod çok basit ve kısadır ( açıklama ). FP'ye yazarsanız, karşılaştırmak ilginç olacaktır.
Rica ederim. FP stilinde C#:
FP elbette çok çarpıktır (FP kodlayıcısı çarpık kodlayıcıyı alt FP dilinde C# yazdığı için) Ama amaç modern OOP YaP'larda bunun FP'de mümkün olduğunu göstermektir. Sınırlı tabi ki bu F# veya Haskell değil ama kimse FP tarzında yazmayı yasaklamıyor. Değişmezlik, daha yüksek dereceli işlevler, kapatmalar, eşlemeler vb. kullanın. - her şey mümkün, lütfen. Sadece bundan gelen kod bir nedenden dolayı ideal hale gelmiyor.
ps Kodun genel yapısı kasıtlı olarak orijinali taklit eder. FP'de iyi bir şekilde, karmaşık nesneler ve foreach bir Haritayı taklit etmeden tamamen farklı bir şekilde gerekli olsa da, sanatçı elinden gelenin en iyisini yaptı.
Rica ederim. FP stilinde C#:
Bunun bir alışkanlık ve sözdizimi bilgisi meselesi olduğunu anlıyorum, ancak orijinalin yazarı olmama rağmen kodu girmek benim için çok zor.
Ticaret, otomatik ticaret sistemleri ve ticaret stratejilerinin test edilmesi hakkında forum
OOP'a ilginç bir bakış
fxsaber , 2021.01.29 13:39
Ayak bezi.
Resmi olarak, bu OOP'dir. Ama en ilkel kısmı. Ancak, onsuz yaşayamazdı. Belki aptalca, beyin başka bir şeye dönüştü ve ben bunu perçinledim.