题目的大意是用一个类封装位运算,并通过位运算实现四则运算。我一下子就想起了bitset,但是bitset并不支持四则运算。后来想想也许叫大整数类比较合适吧。
当然还是有很多问题的,有些问题是写完了才发现的,当时发着高烧,一边写一边debug,好不容易赶到deadline前,交过之后也没有改的动力了……
首先是该用友元实现的二元关系的运算符全写在类内了,写之前应该看看书的。其次是没有实现下标运算符的重载,这个要用到设计模式中的代理模式,同样是没来得及写,这里有篇blog里面实现了:
http://blog.csdn.net/fastsort/article/details/8922923
一些其他问题写在了实验报告中。
bit.h
#pragma once
#include
#include
#include
#define BLOCK (len_ / (8 * sizeof(size_t)) + (len_ % (sizeof(size_t) * 8)? 1: 0))
#define BLOCKBIT (8 * sizeof(size_t))
using namespace std;
template //len_ is the number of bit(s)
class myBitset {
friend ostream& operator<< (ostream &out, const myBitset& bs)
{
// stored reversely, so output reversely
for (size_t i = 0; i < len_; i ++) {
if (bs.isTrue(len_ - i - 1)) out << "1";
else out << "0";
// printf("%d ",i);
}
return out;
}
public:
myBitset() : block_(BLOCK)
{
num_ = new size_t[block_];
memset(num_, 0, block_ * sizeof(size_t));
// printf("%d %d %d\n", block_, sizeof(size_t), block_ * sizeof(size_t));
// for (int i = 0; i < block_; i ++) num_[i] = 0;
// cout << *this << endl;
}
myBitset(const myBitset& bs);
//invert signed number to myBitset, and avoid ambiguous calling for overloaded functions
myBitset(signed int num);
myBitset(unsigned int num);
myBitset(signed long);
myBitset(unsigned long);
// myBitset(signed long long);
// myBitset(unsigned long long);
myBitset(signed __int64 num);
myBitset(unsigned __int64 num);
myBitset(const string& s);
~myBitset();
myBitset& operator= (const myBitset& bs);
myBitset operator& (const myBitset& bs) const;
myBitset operator| (const myBitset& bs) const;
myBitset operator~ (void) const;
myBitset operator^ (const myBitset& bs) const;
// BOTH TWO BELOW ARE LOGICAL SHIFT! BE CAREFUL !
myBitset operator<< (size_t shift) const;
myBitset operator>> (size_t shift) const;
myBitset& operator&= (const myBitset& bs);
myBitset& operator|= (const myBitset& bs);
myBitset& operator^= (const myBitset& bs);
myBitset& operator<<= (size_t shift);
myBitset& operator>>= (size_t shift);
myBitset& operator++ (void);
myBitset& operator-- (void);
myBitset operator++ (int dummy);
myBitset operator-- (int dummy);
// in operator+= we need local variables of myBitset, so argument is not reference
myBitset& operator+= (myBitset bs);
myBitset& operator-= (const myBitset& bs);
myBitset operator+ (const myBitset& bs) const;
myBitset operator- (const myBitset& bs) const;
myBitset operator+ (void) const;
myBitset operator- (void) const;
myBitset operator* (const myBitset& bs) const;
myBitset operator/ (const myBitset& bs) const;
// myBitset operator% (const myBitset& bs) const;
myBitset& operator*= (myBitset bs);
myBitset& operator/= (myBitset bs);
bool operator> (const myBitset& bs) const;
bool operator>= (const myBitset& bs) const;
bool operator< (const myBitset& bs) const;
bool operator<= (const myBitset& bs) const;
bool operator== (const myBitset& bs) const;
bool operator!= (const myBitset& bs) const;
explicit operator bool(void) const;
void flip();// flip all bits
void set(size_t index);
void reset(size_t index);
bool isTrue(size_t index) const;
size_t getBlock(void) { return block_;}
size_t getLen(void) { return len_;}
private:
size_t* num_; //pointer to where the bits stored
const size_t block_; //the size of the array
};
template myBitset::myBitset(const myBitset& bs) :
block_(bs.block_)
{
num_ = new size_t[block_];
for (size_t i = 0; i < bs.block_; i ++)
num_[i] = bs.num_[i];
}
// lower bit is stored in the smaller index
template myBitset::myBitset(unsigned __int64 num) : myBitset()
{
size_t p = 0;
// printf("%llu\n",num);
while (num && p < len_) {
if (num & 1) {
set(p);
// printf("%d\n",p);
}
++ p;
num >>= 1;
}
// size_t is an unsigned type !!
}
//template myBitset::myBitset(unsigned long long num) :
// myBitset(unsigned __int64(num)) {}
template myBitset::myBitset(unsigned long num) :
myBitset(static_cast<unsigned __int64>(num)) {}
template myBitset::myBitset(unsigned int num) :
myBitset(static_cast<unsigned __int64>(num)) {}
template myBitset::myBitset(signed __int64 num) :
myBitset(static_cast<unsigned __int64>(abs(num)))
{
if (num < 0) {
flip();
++ (*this);
}
}
//template myBitset::myBitset(signed long long num) :
// myBitset(signed __int64(num)) {}
template myBitset::myBitset(signed long num) :
myBitset(static_cast<signed __int64>(num)) {}
template myBitset::myBitset(signed int num) :
myBitset(static_cast<signed __int64>(num)) {}
template myBitset::myBitset(const string& s) : myBitset()
{
for (size_t i = 0; i < s.size(); i ++) {
if (s[i] != '0') {
set(s.size() - i - 1);
}
}
}
template myBitset::~myBitset()
{
delete []num_;
}
template inline void myBitset::set(size_t index)
{
// 1不加强制类型转换为什么会出现循环左移……
num_[index / BLOCKBIT] |= (size_t(1) << (index % BLOCKBIT));
// printf("%d %d %d\n",index, index / BLOCKBIT, index % BLOCKBIT);
return ;
}
template inline void myBitset::reset(size_t index)
{
num_[index / BLOCKBIT] &= ~(size_t(1) << (index % BLOCKBIT));
return ;
}
template inline bool myBitset::isTrue(size_t index) const
{
// if (num_[index / BLOCKBIT] & (size_t(1) << (index % BLOCKBIT))) printf(" %d %d %d\n",index, index / BLOCKBIT,index %BLOCKBIT);
// printf("%llu\n",1 << (index % BLOCKBIT));
return num_[index / BLOCKBIT] & (size_t(1) << (index % BLOCKBIT));
}
template inline void myBitset::flip(void)
{
for (size_t i = 0; i < block_; i ++) {
num_[i] = ~num_[i];
}
return ;
}
template myBitset& myBitset::operator= (const myBitset& bs)
{
if (this != &bs) {
for (size_t i = 0; i < block_; i ++)
num_[i] = bs.num_[i];
}
}
template myBitset myBitset::operator&(const myBitset& bs) const
{
myBitset tbs(*this);
tbs &= bs;
return tbs;
}
template myBitset myBitset::operator|(const myBitset& bs) const
{
myBitset tbs(*this);
tbs |= bs;
return tbs;
}
template myBitset myBitset::operator~(void) const
{
myBitset tbs(*this);
tbs.flip();
return tbs;
}
template myBitset myBitset::operator^(const myBitset& bs) const
{
myBitset tbs(*this);
tbs ^= bs;
return tbs;
}
template myBitset myBitset::operator<<(size_t shift) const
{
myBitset tbs(*this);
tbs <<= shift;
return tbs;
}
template myBitset myBitset::operator>>(size_t shift) const
{
myBitset tbs(*this);
tbs >>= shift;
return tbs;
}
template myBitset& myBitset::operator&= (const myBitset& bs)
{
for (size_t i = 0; i < block_; i ++) {
num_[i] &= bs.num_[i];
}
return *this;
}
template myBitset& myBitset::operator|= (const myBitset& bs)
{
for (size_t i = 0; i < block_; i ++) {
num_[i] |= bs.num_[i];
}
return *this;
}
template myBitset& myBitset::operator^= (const myBitset& bs)
{
for (size_t i = 0; i < block_; i ++) {
num_[i] ^= bs.num_[i];
}
return *this;
}
template myBitset& myBitset::operator<<= (size_t shift)
{
if (shift == 0) return *this;
if (shift >= len_) {
memset(num_, 0, block_ * sizeof(size_t));
return *this;
}
size_t blockShift = shift / BLOCKBIT; // the shift of how many units of array
size_t innerShift = shift % BLOCKBIT; // the shift in the unit of array
for (size_t i = 0; i < block_; i ++) {
size_t opid = block_ - 1 - i;
if (opid < blockShift) {
num_[opid] = 0;
} else {
if (opid - blockShift > 0)
num_[opid]=(num_[opid-blockShift]<1]>>(BLOCKBIT-innerShift));
else
num_[opid] = num_[opid - blockShift] << innerShift;
}
}
return *this;
}
template myBitset& myBitset::operator>>= (size_t shift)
{
// printf("%llu\n",num_[0]);
if (shift == 0) return *this;
if (shift >= len_) {
memset(num_, 0, block_ * sizeof(size_t));
return *this;
}
size_t blockShift = shift / BLOCKBIT; // the shift of how many units of array
size_t innerShift = shift % BLOCKBIT; // the shift in the unit of array
for (size_t i = 0; i < block_; i ++) {
if (i > block_ - 1 - blockShift) {
num_[i] = 0;
} else {
if (i + blockShift + 1 < block_)
num_[i]=(num_[i+blockShift]>>innerShift)|(num_[i+blockShift+1]<<(BLOCKBIT-innerShift));
else
num_[i] = num_[i + blockShift] >> innerShift;
}
}
// printf("%llu\n",tbs.num_[0]);
return *this;
}
template inline myBitset& myBitset::operator++ (void)
{
(*this) += 1;
return *this;
}
template inline myBitset myBitset::operator++ (int dummy)
{
myBitset tbs = (*this);
++ (*this);
return tbs;
}
template inline myBitset& myBitset::operator-- (void)
{
(*this) -= 1;
return *this;
}
template inline myBitset myBitset::operator-- (int dummy)
{
myBitset tbs = (*this);
-- (*this);
return tbs;
}
template inline myBitset myBitset::operator+ (const myBitset& bs) const
{
myBitset tbs(*this);
tbs += bs;
return tbs;
}
template inline myBitset myBitset::operator- (const myBitset& bs) const
{
myBitset tbs(*this);
tbs += -bs;
return tbs;
}
template inline myBitset& myBitset::operator-= (const myBitset& bs)
{
*this += -bs;
return *this;
}
template inline myBitset& myBitset::operator+= (myBitset bs)
{
myBitset tbs;
while ((bs)) {
tbs = (*this) ^ bs;
bs = (*this & bs) << 1;
*this = tbs;
}
return *this;
}
template inline myBitset myBitset::operator+ (void) const
{
return *this;
}
template inline myBitset myBitset::operator- (void) const
{
myBitset tbs(*this);
return ~(tbs) + 1;
}
template myBitset::operator bool(void) const
{
for (size_t i = 0; i < len_ ; i ++) {
if (isTrue(i))
return true;
}
return false;
}
template myBitset& myBitset::operator*= (myBitset bs)
{
if (!bs || !*this) {
*this = 0;
return *this;
}
int flag = 0;
myBitset tbs(*this);
*this = 0;
if (isTrue(len_ - 1)) {
flag = ~flag;
tbs = -tbs;
}
if (bs.isTrue(len_ - 1)) {
flag = ~flag;
bs = -bs;
}
while (bs) {
if (bs & 1)
*this += tbs;
tbs <<= 1;
bs >>= 1;
}
if (flag) {
*this = -(*this);
}
return *this;
}
template myBitset myBitset::operator* (const myBitset& bs) const
{
myBitset tbs(*this);
tbs *= bs;
return tbs;
}
template myBitset& myBitset::operator/= (myBitset bs)
{
// cout << *this << " " << bs << endl;
if (bs) {
int flag = 0;
myBitset tbs(*this);
*this = 0;
if (tbs.isTrue(len_ - 1)) {
flag = ~flag;
tbs = -tbs;
}
if (bs.isTrue(len_ - 1)) {
flag = ~flag;
bs = -bs;
}
// cout << tbs << " " << bs << endl;
size_t highbit = 0;
for (size_t i = len_ - 2; i > 0; i --) {
if (tbs.isTrue(i)) {
highbit = i;
break;
}
}
for (size_t i = 0; i <= highbit; i ++) {
size_t op = highbit - i;
// avoid overflow!!!
if ((tbs >> op) >= bs) {
tbs -= (bs << op);
*this += (myBitset(1) << op);
}
// cout << op << " " << tbs << " " << bs << " " << *this << endl;
}
if (flag) {
*this = -(*this);
}
return *this;
} else {
cout << "divisor cannot be 0 !" << endl;
return *this;
}
}
template myBitset myBitset::operator/ (const myBitset& bs) const
{
myBitset tbs(*this);
tbs /= bs;
return tbs;
}
template bool myBitset::operator>= (const myBitset& bs) const
{
return (*this > bs || *this == bs);
}
template bool myBitset::operator> (const myBitset& bs) const
{
if (!isTrue(len_ - 1) && isTrue(len_ - 1)) {
return true;
}
if (isTrue(len_ - 1) && !isTrue(len_ - 1)) {
return false;
}
for (size_t i = 0; i < block_; i ++) {
size_t op = block_ - i - 1;
if (num_[op] > bs.num_[op]) {
return true;
}
if (num_[op] < bs.num_[op]) {
return false;
}
}
return false;
}
template bool myBitset::operator== (const myBitset& bs) const
{
if (*this ^ bs) {
return false;
} else {
return true;
}
}
template inline bool myBitset::operator< (const myBitset& bs) const
{
return !(*this >= bs);
}
template inline bool myBitset::operator<= (const myBitset& bs) const
{
return !(*this > bs);
}
template inline bool myBitset::operator!= (const myBitset& bs) const
{
return !(*this == bs);
}
main.cpp
里面主要是测试
#include
#include
#include "bit.h"
#include
using namespace std;
int main(int argc, char** argv)
{
cout << (-11111 >> 30) << endl;
cout << size_t(-1) << endl;
cout << "test for set, reset and flip" << endl;
myBitset<32> bt;
bt.set(0);
cout << bt << endl;
bt.reset(0);
cout << bt << endl;
bt.set(31);
cout << bt << endl;
bt.flip();
cout << bt << endl;
cout << endl << "test for constructor" << endl;
string s = "100010";
myBitset<32> bt1;
cout << bt1 << endl;
myBitset<33> bt2(s);
cout << bt2 << endl;
myBitset<33> bt31(64);
cout << bt31 << endl;
myBitset<65> bt32(static_cast<unsigned long long>((size_t(1) << 63) + ((size_t(1) << 63) - 1)));
cout << bt32 << endl;
myBitset<33> bt4(bt31);
cout << bt4 << endl;
cout << endl << "test for <<, >> and =" << endl;
myBitset<100> bt5(size_t(pow(2,31))+15);
cout << bt5 << endl;
cout << (bt5 << 4) << endl;
cout << (bt5 >> 4) << endl;
cout << (size_t(1) << 33) << endl;
myBitset<100> bt6("100000011111111111000010101");
cout << bt6 << endl;
bt6 = bt5;
cout << bt6 << endl;
myBitset<129> bt7 = string("10110011101111011111010101");
cout << bt7 << endl;
cout << (bt7 >> 7) << endl;
cout << (bt7 << 7) << endl;
cout << (bt7 << 65) << endl;
cout << (bt7 >> 65) << endl;
cout << endl << "test for &, |, ~ and ^" << endl;
myBitset<70> bt8("1011011101111011111011111101111111011111111011111111101111111111011110");
cout << bt8 << endl;
myBitset<70> bt9(~bt8);
cout << bt9 << endl;
cout << (bt8 | bt9) << endl;
cout << (bt8 & bt9) << endl;
cout << (bt8 ^ bt9) << endl;
cout << (bt8 ^ bt9 ^ bt8) << endl;
cout << endl << "test for &=, |= and ^=" << endl;
cout << bt8 << endl;
bt8 &= bt9;
cout << bt8 << endl;
bt8 |= bt9;
cout << bt8 << endl;
bt8 ^= ~bt9 ^ 1;
cout << bt8 << endl;
cout << endl << "test for <<= and >>=" << endl;
myBitset<70> bt10("1011011101111011111011111101111111011111111011111111101111111111011111");
cout << bt10 << endl;
cout << (bt10 << 65) << endl;
bt10 <<= 65;
cout << bt10 << endl;
bt10 = string("1011011101111011111011111101111111011111111011111111101111111111011111");
cout << (bt10 >> 65) << endl;
bt10 >>= 65;
cout << bt10 << endl;
cout << endl << "test for + and -" << endl;
bt9 = string("1011011101111011111011111101111111011111111011111111101111111111011111");
bt10 = ~bt9;
cout << bt9 << endl;
cout << bt10 << endl;
cout << (-bt9) << endl;
cout << (-bt10) << endl;
cout << (bt9 + bt10) << endl;
cout << (bt9 - (bt10>>3)) << endl;
bt9 = -1;
bt10 = 64;
cout << (bt9 + bt10) << endl;
cout << (bt9 - bt10) << endl;
cout << endl << "test for ++, -- , += and -=" << endl;
bt9 = string("1011011101111011111011111101111111011111111011111111101111111111011111");
bt10 = ~bt9;
cout << (bt9 ++) << endl;
cout << bt9 << endl;
cout << (bt10 --) << endl;
cout << bt10 << endl;
cout << (++ bt9) << endl;
cout << bt9 << endl;
cout << (-- bt10) << endl;
cout << bt10 << endl;
bt10 += 1;
cout << bt10 << endl;
bt10 -= 3;
cout << bt10 << endl;
cout << endl << "test for *, *=, /, /=" << endl;
bt9 = -13;
bt10 = 3;
bt9 *= bt10;
cout << bt9 << endl;
cout << (bt9 * bt10) << endl;
bt9 *= -3;
bt10 *= 100;
cout << bt9 << endl;
cout << bt10 << endl;
cout << endl << "test for /, /=" << endl;
bt9 = 10;
bt10 = 3;
cout << (bt9 >= bt10) << endl;
cout << (bt9 >> 3) << endl;
cout << ((bt9 >> 3) >= bt10) << endl;
cout << (bt9 << 0) << endl;
cout << (myBitset<70>(1) << 0) << endl;
bt9 /= bt10;
cout << bt9 << endl;
bt9 = -10;
bt10 = 3;
cout << (bt9 / bt10) << endl;
cout << (bt10 / bt9) << endl;
return 0;
}
附:实验报告
位运算的封装:
第一次看到这个题目,我想到了stl中的bitset,bitset实现了对bit类型数组的封装,同时支持六种位运算,我的目的就是实现类似于bitset的类模版。
六种位运算& | ~ ^ << >> 支持基础数据类型,但是基础数据类型的大小是固定的,不能支持bit数高于8 * sizeof(size_t)(最大一般是64bit)的要求,而且不能支持任意位数的bit类型数组,这样显然不能满足我们的要求。
因此,我决定使用size_t类型的数组,通过基础类型的位运算实现对每一个size_t内的位的操作,从而实现对抽象的“位类型”的操作。
除了最基础的构造函数、析构函数、拷贝运算符,实现了六种位运算,还实现了布尔类型的类型转换,逻辑运算,和+-*/四则运算和自增自减运算以及流插入操作符重载。
100!的计算:
首先想到的是高精度乘法,通过数组存储大数的每一位,模拟竖式乘法,从而得解。
这里介绍位运算封装的流程,大数阶乘比较简单。
1. 构造函数:
共9个,最基础的是默认构造函数,在其中完成相关变量初始化和内存空间的申请。
之后是拷贝构造函数,myBitset(unsigned __int64 num); myBitset(const string& s); 它们首先使用默认构造函数进行委托构造,之后再实现自己特定的构造。
在之后是以其他各种无符号或有符号整数做参数的构造函数,它们使用myBitset(unsigned __int64 num);进行委托构造,从而完成功能。
2.基础功能的实现
共4个,分别是
void flip();
void set(size_t index);
void reset(size_t index);
bool isTrue(size_t index) const;
flip实现按位取反,set实现对下标是index的置1,reset是实现对下标是index的置0,isTrue判断下标为index的位是否是1,接下来的许多函数都是需要直接或者间接调用这些函数的。
2. 位运算运算符以及=的重载
myBitset& operator= (const myBitset& bs);
myBitset operator& (const myBitset& bs) const;
myBitset operator| (const myBitset& bs) const;
myBitset operator~ (void) const;
myBitset operator^ (const myBitset& bs) const;
myBitset operator<< (size_t shift) const;
myBitset operator>> (size_t shift) const;
myBitset& operator&= (const myBitset& bs);
myBitset& operator|= (const myBitset& bs);
myBitset& operator^= (const myBitset& bs);
myBitset& operator<<= (size_t shift);
myBitset& operator>>= (size_t shift);
首先实现的是&= |= 等函数,之后& |等运算符通过调用&= |= 等实现功能。
3. 四则运算与自增自减
myBitset& operator++ (void);
myBitset& operator– (void);
myBitset operator++ (int dummy);
myBitset operator– (int dummy);
myBitset& operator+= (myBitset bs);
myBitset& operator-= (const myBitset& bs);
myBitset operator+ (const myBitset& bs) const;
myBitset operator- (const myBitset& bs) const;
myBitset operator+ (void) const;
myBitset operator- (void) const;
myBitset operator* (const myBitset& bs) const;
myBitset operator/ (const myBitset& bs) const;
myBitset& operator*= (myBitset bs);
myBitset& operator/= (myBitset bs);
同样,首先实现的是+= -=等,对应的双目运算符则调用前者,单目-调用~运算符。
前置自增自减调用+= -=,而后置自增自减调用前置自增自减。
4. 逻辑运算符与bool类型转换
bool operator> (const myBitset& bs) const;
bool operator>= (const myBitset& bs) const;
bool operator< (const myBitset& bs) const;
bool operator<= (const myBitset& bs) const;
bool operator== (const myBitset& bs) const;
bool operator!= (const myBitset& bs) const;
explicit operator bool(void) const;
bool类型转换函数调用isTrue函数。
实现的是>和==,其他逻辑运算符直接或间接调用这两个函数。
1.构造函数
为了支持四则运算,必须提供参数无符号整型和有符号整型的构造函数,开始我只定义了unsigned __int64和 signed __int64为参数的构造函数,然而这时就会遇到二义调用的问题。
为了避免二义调用,我为常见的整型类型分别定义了构造函数。
2.移位运算
因为存储位的是数组,故实现移位操作时会遇到困难,通过寻找规律可以解决这一问题。
此外还遇到了如下问题。
一开始我并没有对1进行强制类型转换,转换成myBitset类型,按道理,1移位超过int位长时,这样会使1移位后的结果变成0(逻辑移位),但是,这里实际上竟然是循环移位。
而单单对1进行左移位,得到的结果是逻辑移位的结果。
目前还是没有弄明白是为什么。
因为首先实现的是<<=和>>= ,<< >>是通过调用<<= >>= 实现的,移位的时候可能会出现运算结果覆盖未进行运算数据的情况,所以要注意运算的顺序,>>要先从低位开始算,<<要先从高位开始算。
还遇到了移位0时出现的错误,需要特判shift为0时的情况。(除法调用移位操作时发现)
3.bool类型转换
一开始并没有把operator bool 声明为explicit,于是出现了双目运算符调用时的二义调用(左操作数为myBitset对象而右操作数为基础数据类型时),因为myBitset可以隐式的转换为bool类型,c++中bool类型实质上就是int类型。
在查资料之前,我尝试了在声明中加入了explicit关键字,尽管在我的印象中它只能用在构造函数的声明中,但是问题的确解决了,后来查资料发现,在c++11标准中,允许在类型转换运算符前加入explicit的声明,而对bool则更加特殊,在条件表达式中它允许隐式转换而在其他情况中只允许显式使用。
5. 不小心就会发生的间接递归
由于一些运算符要通过调用其他运算符实现,所以在头脑不清晰的情况下极易发生
递归,而且这类错误比较难发现,程序中出现的最长间接递归链甚至可达10个以上的函数。
6. 乘法与除法
在设计乘法的算法时我借鉴了快速幂算法的思想,只不过当第二个乘数为奇数时ans变量做的运算由乘变成了加,只要调用加法就可以实现乘法了。
除法就是乘法的逆运算。
7. size_t类型
size_t类型是一种无符号整数类型,具体类型依赖于环境,但它是非负的,用size_t类型做循环变量时,由于它不可能小于0,于是下面的语句会出现死循环。
For (size_t I = len_ - 1; I >= 0; I ++)
故程序中所有循环尽量写成正序的,需要反向的顺序时,通过循环变量计算出实际运算的下标。
封装位运算操作符
优点:
a) 实现了任意长度的位类型
b) 满足了所有的要求
c) 尽量使用已定义的方法去定义其他方法
d) 对于多个方法(已实现的或是以后可能实现的)会使用的相同方法,将该方法定义为一个函数
e) 实现了四则运算,自增自减,重载了流插入操作符。
缺点:
a) 最重大的失误:没有将二元运算符用非成员函数实现。(3 + myBitset<10>(1)是非法的)
b) 没有实现[]操作符。(代理模式)
c) 没有用myBitset类实现阶乘(主要是没有转换成整型的方法)
d) 没有定义将myBitset转换为整型的方法(大数进制转换)
e) 部分方法效率不高