2016-06-07 45 views
5

Son bir projede, yanlışlıkla bir dize başvurusuna bir kayan nokta atadığım bir hatayla karşılaştım (floatın bir dizeye dönüştürülmesi yerine, atama). dize açıkça çöp sonuçlanır YazdırmaBir dize referans çalışması için bir float atama - neden?

#include <iostream> 
using namespace std; 

static void get_text(string &s) { 
    s = 1.0f; // Legal (not even a warning!) 
} 

// This version gives a compiler error (as I'd expect) 
// static void get_text(string &s) { 
//  string out = 1.0f; 
//  s = out; 
// } 

int main() { 
    string s; 
    get_text(s); 
    cout << s << endl; // Prints garbage 
    return 0; 
} 

, ama neden bu yapmadım net değilim:

kodu (her ikisi Xcode/Apple LLVM 7.1 ve GCC 4.9.2 altında test) böyle bir şey görünüyordu Uyarı olarak çok ver. (En iyi tahminim, derleyicinin float'tan int'ye, bir bellek adresine gitmesi için bir tür örtülü yeniden yorumlama yapmasıydı ...?)

Etkinleştirebileceğim bir uyarı var mı (Xcode'da, ideal olarak) Gelecekte bu tür şeyleri engeller mi?

cevap

8

Bu, eleman fonksiyonu olan: C türleri tamsayı kayan nokta örtük dönüşüm ++ vardır

string& operator=(char ch); 

(char bir tamsayıdır tip).

Normal olarak, bu dönüşüm hakkında bir uyarı almak için -Wfloat-conversion g ++ 'yi kullanabilirsiniz, ancak bunu denedim ve uyarmadım. (? Belki hata derlemek)

basit bir yolu beklenmedik yüzen/tamsayı dönüşümleri için hataları almak için kodunu değiştirmek için:

s = { 1.0f }; 

Diğer bir seçenek işlev dönüş türü olarak string sahip hale getirmektir (genel anlamda Bu tasarım) yine bir "dışarı" referans parametresine sahip olması tercih edilir:

static string get_text() { return 1.0f; } 

ne yazık ki, bu C++ hala çok genç-yetişkin zaman "tasarlanmış" edilmiştir std::string kullanımını çevreleyen çok sayıda küçük tuzaklar biridir g ve istenmeyen uzun vadeli sonuçların ortaya çıkacağı açık değildi.

+0

Büyüleyici. Posterity uğruna, 'std :: string' içinde bir 'operator = (char c)' varken bunu ekleyeceğim, tek bir karakteri alan bir müteahhit değil --- 'get_text()' in ikinci sürümü soruda derlenmez. Okumak için ikinci sürümü değiştirirsem: 'string out; out = (char) 1.0f; ', derleme yapar. – s3cur3