|
|
/**
|
|
|
* @file WDouble.h
|
|
|
* @brief double型变量封装,可以设置精度
|
|
|
* @author 沙漠乌鸦
|
|
|
* @date 2009-09-07
|
|
|
* @warning WDouble类暂时需要实现的功能
|
|
|
* 1) 设置全局的默认精度和单独的精度
|
|
|
* 2) 返回原始double值或运用精度计算后的值
|
|
|
* 3) 同时支持正、负数的格式化
|
|
|
* 3) 大小比较符<、>、<=、>=
|
|
|
* 4) ==、!=操作符
|
|
|
* 5) +、-、*、/、+=、-=、*=、/=操作符
|
|
|
* 6) <<、>>操作符
|
|
|
*/
|
|
|
|
|
|
#pragma once
|
|
|
#include <iostream>
|
|
|
using std::ostream;
|
|
|
using std::istream;
|
|
|
|
|
|
namespace wuya
|
|
|
{
|
|
|
|
|
|
class AFX_EXT_CLASS WDouble
|
|
|
{
|
|
|
public:
|
|
|
WDouble(void);
|
|
|
WDouble(double dVal,size_t nPrecision = GetPrecisionDef());
|
|
|
WDouble(const WDouble& dVal);
|
|
|
~WDouble(void) throw();
|
|
|
|
|
|
WDouble& operator = (const WDouble& dVal);
|
|
|
WDouble& operator = (double dVal);
|
|
|
|
|
|
// operator
|
|
|
friend inline bool operator == (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline bool operator != (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline bool operator < (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline bool operator > (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline bool operator <= (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline bool operator >= (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline void operator += (WDouble& dVal1,const WDouble& dVal2); ///< 精度以第一个操作数为准
|
|
|
friend inline void operator -= (WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline void operator *= (WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline void operator /= (WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline WDouble operator + (const WDouble& dVal1,const WDouble& dVal2); ///< 精度以精度较大的为准
|
|
|
friend inline WDouble operator - (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline WDouble operator * (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline WDouble operator / (const WDouble& dVal1,const WDouble& dVal2);
|
|
|
friend inline ostream& operator << (ostream& os,const WDouble& object);
|
|
|
friend inline istream& operator >> (istream& is,WDouble& object);
|
|
|
|
|
|
/**
|
|
|
* @brief 设置WDouble精度
|
|
|
* @param [in]nPrecision 由于double型精度最大支持10位,该值范围为0-10,若非该范围值,则保留原精度
|
|
|
*/
|
|
|
void SetPrecision(size_t nPrecision);
|
|
|
/** @brief 返回WDoule精度 */
|
|
|
size_t GetPrecision() const;
|
|
|
|
|
|
/**
|
|
|
* @brief 返回double值,精度为WDouble保存精度
|
|
|
*/
|
|
|
double Get() const;
|
|
|
/**
|
|
|
* @brief 返回double值,精度为nPrecision
|
|
|
*/
|
|
|
double Get(size_t nPrecision) const;
|
|
|
/**
|
|
|
* @brief 返回输入的double值、未进行四舍五入
|
|
|
*/
|
|
|
double GetEnter() const;
|
|
|
|
|
|
static void SetPrecisionDef(size_t nPrecision);
|
|
|
static size_t GetPrecisionDef();
|
|
|
|
|
|
private:
|
|
|
/** @brief 对原始数据进行四舍五入计算 */
|
|
|
double Round(size_t nPrecision) const;
|
|
|
|
|
|
void Round();
|
|
|
|
|
|
private:
|
|
|
double m_dDbl; ///< 按照精度四舍五入后的double值
|
|
|
double m_dDblEnter; ///< 原始double值
|
|
|
size_t m_nPrecision; ///< double精度
|
|
|
|
|
|
static size_t m_nPrecisionDef; ///< 默认精度、值为1,即可以精确到0.1
|
|
|
};
|
|
|
|
|
|
//operator
|
|
|
inline bool operator == (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
return dVal1.m_dDbl == dVal2.m_dDbl;
|
|
|
}
|
|
|
inline bool operator != (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
return dVal1.m_dDbl != dVal2.m_dDbl;
|
|
|
}
|
|
|
inline bool operator < (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
return dVal1.m_dDbl < dVal2.m_dDbl;
|
|
|
}
|
|
|
inline bool operator > (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
return dVal1.m_dDbl > dVal2.m_dDbl;
|
|
|
}
|
|
|
inline bool operator <= (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
return dVal1.m_dDbl <= dVal2.m_dDbl;
|
|
|
}
|
|
|
inline bool operator >= (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
return dVal1.m_dDbl >= dVal2.m_dDbl;
|
|
|
}
|
|
|
inline void operator += (WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
dVal1.m_dDblEnter += dVal2.m_dDblEnter;
|
|
|
|
|
|
// 以dVal1的精度为准
|
|
|
dVal1.Round();
|
|
|
}
|
|
|
inline void operator -= (WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
dVal1.m_dDblEnter -= dVal2.m_dDblEnter;
|
|
|
|
|
|
// 以dVal1的精度为准
|
|
|
dVal1.Round();
|
|
|
}
|
|
|
inline void operator *= (WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
dVal1.m_dDblEnter *= dVal2.m_dDblEnter;
|
|
|
|
|
|
// 以dVal1的精度为准
|
|
|
dVal1.Round();
|
|
|
}
|
|
|
inline void operator /= (WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
dVal1.m_dDblEnter /= dVal2.m_dDblEnter;
|
|
|
|
|
|
// 以dVal1的精度为准
|
|
|
dVal1.Round();
|
|
|
dVal1.m_dDblEnter = dVal1.m_dDbl;
|
|
|
}
|
|
|
inline WDouble operator + (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
size_t nPrecision;
|
|
|
if(dVal1.m_nPrecision > dVal2.m_nPrecision)
|
|
|
nPrecision = dVal1.m_nPrecision;
|
|
|
else
|
|
|
nPrecision = dVal2.m_nPrecision;
|
|
|
|
|
|
WDouble dVal(dVal1.m_dDbl + dVal2.m_dDbl,nPrecision);
|
|
|
return dVal;
|
|
|
}
|
|
|
inline WDouble operator - (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
size_t nPrecision;
|
|
|
if(dVal1.m_nPrecision > dVal2.m_nPrecision)
|
|
|
nPrecision = dVal1.m_nPrecision;
|
|
|
else
|
|
|
nPrecision = dVal2.m_nPrecision;
|
|
|
|
|
|
WDouble dVal(dVal1.m_dDbl - dVal2.m_dDbl,nPrecision);
|
|
|
return dVal;
|
|
|
}
|
|
|
inline WDouble operator * (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
size_t nPrecision;
|
|
|
if(dVal1.m_nPrecision > dVal2.m_nPrecision)
|
|
|
nPrecision = dVal1.m_nPrecision;
|
|
|
else
|
|
|
nPrecision = dVal2.m_nPrecision;
|
|
|
|
|
|
WDouble dVal(dVal1.m_dDbl * dVal2.m_dDbl,nPrecision);
|
|
|
return dVal;
|
|
|
}
|
|
|
inline WDouble operator / (const WDouble& dVal1,const WDouble& dVal2)
|
|
|
{
|
|
|
size_t nPrecision;
|
|
|
if(dVal1.m_nPrecision > dVal2.m_nPrecision)
|
|
|
nPrecision = dVal1.m_nPrecision;
|
|
|
else
|
|
|
nPrecision = dVal2.m_nPrecision;
|
|
|
|
|
|
WDouble dVal(dVal1.m_dDbl / dVal2.m_dDbl,nPrecision);
|
|
|
return dVal;
|
|
|
}
|
|
|
inline ostream& operator << (ostream& os,const WDouble& object)
|
|
|
{
|
|
|
os << object.m_dDbl;
|
|
|
|
|
|
return os;
|
|
|
}
|
|
|
inline istream& operator >> (istream& is,WDouble& object)
|
|
|
{
|
|
|
double dVal;
|
|
|
is >> dVal;
|
|
|
|
|
|
if(is)
|
|
|
{
|
|
|
object.m_dDblEnter = dVal;
|
|
|
object.Round();
|
|
|
}
|
|
|
else
|
|
|
object = WDouble();
|
|
|
|
|
|
return is;
|
|
|
}
|
|
|
|
|
|
}; |