Ho giocato in giro con C++ 11 ultimamente, e si avvicinò con la seguente funzione somma:Il compilatore non avvisa sulla perdita di precisione?
template <typename T>
inline T sum(const std::function<T (int)> &f, int initial, int end)
{
T retval = 0;
for(int k = initial; k <= end; k++) {
retval += f(k);
}
return retval;
}
L'idea è che posso passare una funzione lambda e quindi avere una funzione di pulito e leggibile per matematica somme. Allora ho provato la seguente:
int main()
{
std::array<double, 2> arr1 = {{ 0.5, 1.5 }},
arr2 = {{ 1.5, -0.5 }};
auto n = sum<int>([&](int k) { return arr1[k]*arr2[k]; }, // Precision loss!
0, 1);
return 0;
}
ho compilato questo usando g ++ 4.6.3: g++ -Wall -pedantic -std=c++0x -o test main.cpp
e non dà alcun avviso circa la perdita di precisione ho osservato nel commento del codice sorgente.
È praticamente un dato di fatto che sum<int>
è una brutta cosa da fare, ma potrebbe non essere così ovvio in contesti più complessi. Il compilatore non dovrebbe notare che il valore di ritorno della mia funzione lambda è double
e mi avverte che sto perdendo precisione quando lancio a int
? C'è una ragione specifica che non lo fa?
La funzione non è a conoscenza della precisione perché il runtime esegue un cast implicito prima di passare gli argomenti. Hai ragione, però, in un mondo ideale dovresti almeno vedere un avvertimento in Visual Studio/IDE per riflettere sul fatto che ciò comporterebbe una perdita di precisione. ma non è questo tipo di cosa cosa sono i test unitari? – War
@Wardy in un mondo ideale non sarebbe compilato (cioè sarebbe un errore, non un avvertimento) senza una richiesta esplicita di causare questa perdita di precisione. –
ok ... beh, io sono uno sviluppatore di C# e devo seguire le regole di .net (non sono sicuro se si sta utilizzando anche un compilatore .net ma) afferma nella documentazione che dove è previsto un tipo meno preciso implicito il cast è applicato ... è considerato una caratteristica della lingua. Sono d'accordo però ... un errore sarebbe il sogno assoluto nel tuo scenario ma non comune alla piattaforma nella mia esperienza. – War