问题描述
结构体重载运算符的疑惑
#include<iostream>#include<string>#include<cstring>#include<cstdio>using namespace std;const int N = 1005;struct bign{ int len,s[N]; bign() { memset(s,0,sizeof(s)); len=1; } bign(int num) { *this=num; } bign(char *num) { *this=num; } bign operator =(int num) {char c[N];sprintf(c,'%d',num);*this=c;return *this; } bign operator =(const char *num) {len=strlen(num);for (int i=0;i<len;i++) s[i]=num[len-1-i]-’0’;return *this; } string str() {string res='';for (int i=0;i<len;i++) res=(char)(s[i]+’0’)+res;return res; } void clean() {while (len>1&&!s[len-1]) len--; } bign operator +(const bign &b) {bign c; c.len=0;for (int i=0,g=0;g||i<len||i<b.len;i++){ int x=g; if (i<len) x+=s[i]; if (i<b.len) x+=b.s[i]; c.s[c.len++]=x%10; g=x/10;}return c; } bign operator -(const bign &b) {bign c;c.len=0;int x; for (int i=0,g=0;i<len;i++){ x=s[i]-g; if (i<b.len) x-=b.s[i]; if (x>=0) g=0; else{ x+=10;g=1; }; c.s[c.len++]=x;}c.clean();return c; } bign operator *(const bign &b) {bign c;c.len=len+b.len;for (int i=0;i<len;i++) for (int j=0;j<b.len;j++) c.s[i+j]+=s[i]*b.s[j];for (int i=0;i<c.len-1;i++) { c.s[i+1]+=c.s[i]/10; c.s[i]%=10; }c.clean();return c; } bool operator <(const bign &b) {if (len!=b.len) return len<b.len;for (int i=len-1;i>=0;i--) if (s[i]!=b.s[i]) return s[i]<b.s[i];return false; } bign operator +=(const bign &b) {*this=*this+b;return *this; } bign operator -=(const bign &b) {*this=*this-b;return *this; } };istream& operator >>(istream &in,bign &x){ string s; in>>s; x=s.c_str(); return in;}ostream& operator <<(ostream &out,bign &x){ out<<x.str(); return out;}int main(){ bign a,b,c; ios::sync_with_stdio(false); cin>>a>>b;// cout<<a<<endl;// cout<<b<<endl; c=a+b; cout<<c<<endl; return 0;}
中的
bign(int num) { *this=num; }bign(char *num) { *this=num; }
作用是什么?如果删去这两条语句编译仍能正常通过但
bign n=123;
会编译错误,但
bign n;n=123;
能正常编译结构体的初始化不应该是bign n(123);小白试了试发现结果无差别,这是什么原理?望大神相助
问题解答
回答1:引用一个帖子:http://www.cnblogs.com/chio/a...。赋值操作是在两个已经存在的对象间进行的,而初始化是要创建一个新的对象,并且其初值来源于另一个已存在的对象。编译器会区别这两种情况,赋值的时候调用重载的赋值运算符,初始化的时候调用拷贝构造函数。如果类中没有拷贝构造函数,则编译器会提供一个默认的。这个默认的拷贝构造函数只是简单地复制类中的每个成员。
bign n=123;
调用的是拷贝构造函数:
bign(int num) { *this=num; }
你注释到之后当然会出错,而
bign n;n=123;
先调用默认构造函数,然后调用赋值运算符,所以注释掉两个函数后没有错。
你可以自己debug一下。