c ++朋友函数-运算符重载istream >>

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3312269/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 12:36:34  来源:igfitidea点击:

c++ friend function - operator overloading istream >>

c++operator-overloadingfriendoperator-keyword

提问by user399415

My question is in regards to friend functions as well as overloading the << and >>. From my understanding I thought friend functions could (and should) access private member variables directly. However in the case I have here the compiler would only accept my .cxx file when I used "get" functions to obtain each private variable.

我的问题是关于友元函数以及重载<<和>>。根据我的理解,我认为友元函数可以(并且应该)直接访问私有成员变量。但是,在我这里的情况下,当我使用“get”函数获取每个私有变量时,编译器只会接受我的 .cxx 文件。

Here is my header file

这是我的头文件

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;              

Here is my corresponding .cxx file with the implementations for the friend functions

这是我相应的 .cxx 文件,其中包含友元函数的实现

#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;
}

So in this regard the above friend operators compiled correctly. However why is it that my operator >> can access one private variable directly (is >> bignum.digits[i]) but the rest of the private variables need to be retrieved by 'get functions'

所以在这方面上面的朋友操作符编译正确。但是为什么我的操作符 >> 可以直接访问一个私有变量(是 >> bignum.digits[i]),而其余的私有变量需要通过“获取函数”来检索

Below, when I try to write the overload operators in this regard (how I thought friend functions should properly call private variables):

下面,当我尝试在这方面编写重载运算符时(我认为友元函数应该如何正确调用私有变量):

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;
}

I obtain the following errors.

我得到以下错误。

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

The compiler I am using is g++ (Version 3.3.1). Any help is appreciated, thank you.

我使用的编译器是 g++(版本 3.3.1)。任何帮助表示赞赏,谢谢。

Revised:

修改:

I updated the code so the bignum object could access the private variables. I did the following to the friend operator overloading << and it compiled fine. Thanks for the comments, that was a rookie mistake.

我更新了代码,以便 bignum 对象可以访问私有变量。我对朋友运算符重载 << 做了以下操作,它编译得很好。感谢您的评论,这是一个菜鸟错误。

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;
}

However the compiler is still producing errors for the >> operator

然而,编译器仍然为 >> 运算符产生错误

BigNum2.cxx: In function std::istream& csci2270_hw1B::operator>>(std::istream&, csci2270_hw1B::BigNum&)': BigNum2.cxx:208: error: syntax error before)' token

BigNum2.cxx:在函数std::istream& csci2270_hw1B::operator>>(std::istream&, csci2270_hw1B::BigNum&)': BigNum2.cxx:208: error: syntax error before)' 标记中

The >> is supposed to read in a number and the private member variable 'used' is supposed to record the length of the array. I am still somewhat confused on why the compiler accepts

>> 应该读入一个数字,私有成员变量“used”应该记录数组的长度。我仍然对编译器接受的原因有些困惑

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

return is;
}

as opposed to:

与:

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

return is;
}

Any thoughts? thanks.

有什么想法吗?谢谢。

采纳答案by Jerry Coffin

A friend function has access to the class' private data, but it does notget a thispointer to make that automatic, so every access to the class' data (private or otherwise) has to be qualified. For example this:

友元函数可以访问类的私有数据,但它没有获得this自动执行的指针,因此对类数据(私有或其他)的每次访问都必须进行限定。例如这个:

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

needs to be:

需要是:

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

回答by In silico

You haven't qualified usedin the first function - it needs to be bignum.used. The operator overloads are defined at global scope, so they don't get a thispointer. However, the friend functions do have access to the private members of the class.

您没有used在第一个函数中获得资格- 它需要是bignum.used. 运算符重载是在全局范围内定义的,因此它们不会获得this指针。但是,友元函数确实可以访问类的私有成员。

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; 
} 

回答by Priyankar Ghosh

It seems there is an extra ')' in the following line right after bignum.used.

在 bignum.used 之后的下一行中似乎有一个额外的“)”。

 for (size_t i = 0; i < bignum.used**)**; ++i)