2010-07-22 16 views
12

Moje pytanie dotyczy funkcji znajomych i przeciążania < < i >>. Z mojego rozumowania myślałem, że funkcje znajomych mogą (i powinny) mieć bezpośredni dostęp do prywatnych zmiennych członkowskich. Jednak w tym przypadku kompilator zaakceptuje mój plik .cxx tylko wtedy, gdy użyję funkcji "get" w celu uzyskania każdej zmiennej prywatnej.Funkcja znajomego C++ - operator przeciążający istream >>

Oto mój plik nagłówka

class BigNum 
public: 

// CONSTRUCTORS and DESTRUCTORS 
    BigNum();        
    BigNum(int num, size_t optional_base = 10);       
    BigNum(const char strin[], size_t optional_base = 10); 

// MEMBER FUNCTIONS 
    size_t get_digit(size_t index) const; 
    size_t get_used() const; 
    size_t get_capacity() const; 
    size_t get_base() const; 
    bool get_sign() const; 

// FRIEND FUNCTIONS 
    friend std::ostream& operator<<(std::ostream &os, const BigNum &bignum); 
    friend std::istream& operator>>(std::istream &is, BigNum &bignum); 

private: 
    size_t base;    
    size_t *digits;   
    bool positive;   
    size_t used;    

Oto moja odpowiedni plik .cxx z wdrożeń dla znajomego funkcjonuje

#include "file.h" 
#include <cstdlib> 
#include <iostream> 
#include <string> 
#include <cstring> 

using namespace std; 

std::ostream& operator <<(std::ostream &os, const BigNum &bignum) 
{ 
if (bignum.get_sign() == false) 
    os << '-'; 

for (size_t i = 0; i < bignum.get_used(); ++i) 
    os << bignum.get_digit(bignum.get_used() - i - 1); 

return os; 
} 

std::istream& operator >>(std::istream &is, BigNum &bignum) 
{ 
for (size_t i = 0; i < bignum.get_used(); ++i) 
    is >> bignum.digits[i]; 

return is; 
} 

Więc w tym względzie powyższe podmioty przyjaciel skompilowany poprawnie. Dlaczego jednak mój operator >> może uzyskać bezpośredni dostęp do jednej prywatnej zmiennej (is >> bignum.digits [i]), ale pozostałe zmienne prywatne muszą być odzyskane przez 'get functions'

Poniżej, kiedy spróbuj napisać przeciążenie operatorów w tym zakresie (jak myślałem funkcje przyjaciel powinien właściwie nazywać zmienne prywatne):

std::ostream& operator <<(std::ostream &os, const BigNum &bignum) 
{ 
if (bignum.positive == false) 
    os << '-'; 

for (size_t i = 0; i < bignum.used; ++i) 
    os << bignum.digits[used - i - 1]; 

return os; 
} 

std::istream& operator >>(std::istream &is, BigNum &bignum) 
{ 
for (size_t i = 0; i < bignum.used); ++i) 
    is >> bignum.digits[i]; 

return is; 
} 

mogę uzyskać następujące błędy.

BigNum2.cxx: In function `std::ostream& 
    csci2270_hw1B::operator<<(std::ostream&, const csci2270_hw1B::BigNum&)': 
BigNum2.cxx:201: error: `used' undeclared (first use this function) 
BigNum2.cxx:201: error: (Each undeclared identifier is reported only once for 
    each function it appears in.) 
BigNum2.cxx: In function `std::istream& 
    csci2270_hw1B::operator>>(std::istream&, csci2270_hw1B::BigNum&)': 
BigNum2.cxx:208: error: syntax error before `)' token 

Używany kompilator to g ++ (wersja 3.3.1). Każda pomoc jest doceniana, dziękuję.

Revised:

I uaktualniony kod więc obiekt bignum mógł uzyskać dostęp do zmiennych prywatnych. Zrobiłem następujące polecenie do operatora znajomego przeciążającego < < i skompilowałem go dobrze. Dzięki za komentarze, to był nowatorski błąd.

std::ostream& operator <<(std::ostream &os, const BigNum &bignum) 
{ 
if (bignum.positive == false) 
    os << '-'; 

for (size_t i = 0; i < bignum.used; ++i) 
    os << bignum.digits[bignum.used - i - 1]; 

return os; 
} 

Jednak kompilator wciąż błędy dotyczące >> operatora

BigNum2.cxx: funkcja std::istream& csci2270_hw1B::operator>>(std::istream&, csci2270_hw1B::BigNum&)': BigNum2.cxx:208: error: syntax error before)”tokena

The >> ma odczytać w szeregu i prywatny Zmienna członka "used" ma na celu zapisanie długości tablicy. Nadal jestem nieco zdezorientowany, dlaczego kompilator przyjmuje

std::istream& operator >>(std::istream &is, BigNum &bignum) 
{ 
for (size_t i = 0; i < bignum.get_used()); ++i) 
    is >> bignum.digits[i]; 

return is; 
} 

w przeciwieństwie do:

std::istream& operator >>(std::istream &is, BigNum &bignum) 
{ 
for (size_t i = 0; i < bignum.used); ++i) 
    is >> bignum.digits[i]; 

return is; 
} 

jakieś przemyślenia? dzięki.

+1

Co to jest "plik.h" '? – GManNickG

Odpowiedz

9

Funkcja przyjaciel ma dostęp do klasy prywatnych danych, ale robi nie uzyskać this wskaźnik, aby to automatyczny, więc każdy dostępu do klasy danych (prywatny lub inny) musi być wykwalifikowany.Na przykład w ten sposób:

os << bignum.digits[used - i - 1]; 

musi być:

os << bignum.digits[bignum.used - i - 1]; 
+0

dzięki, że poprawił operator << – user399415

5

Nie zakwalifikowano used w pierwszej funkcji - musi to być bignum.used. Przeciążenia operatora są definiowane globalnie, więc nie otrzymują wskaźnika this. Jednak funkcje znajomego mają dostęp do prywatnych członków klasy.

std::ostream& operator <<(std::ostream &os, const BigNum &bignum) 
{ 
    if (bignum.positive == false) 
     os << '-'; 

    for (size_t i = 0; i < bignum.used; ++i) 
     // Note "bignum.used", instead of "used". 
     os << bignum.digits[bignum.used - i - 1];  
    return os; 
} 

std::istream& operator >>(std::istream &is, BigNum &bignum) 
{ 
    for (size_t i = 0; i < bignum.used; ++i) 
     is >> bignum.digits[i]; 

    return is; 
} 
2

Wydaje się, że jest ekstra ')' w poniższej linii tuż po bignum.used.

for (size_t i = 0; i < bignum.used**)**; ++i) 
Powiązane problemy