💎一站式轻松地调用各大LLM模型接口,支持GPT4、智谱、星火、月之暗面及文生图 广告
本章后面的部分讲述复数这样一个例子。复数在数学和工程领域很有用途,许多计算用到了复数。一个复数是实部和虚部之和,记作x+yi,x为实部,y为虚部,i是-1的平方根。 以下为类Complex的定义: ~~~ class Complex { double real, imag; public: Complex () { } Complex (double r, double i) { real = r; imag = i; } }; ~~~ 在类的定义中,实部和虚部是私有的,构造函数是公有的,故加上public标号。 一般使用这样两个构造函数:一个没有参数也不做什么工作的构造函数,另一个有两个参数来用来初始化变量。 到现在为止,还看不到将变量私有化的明显优点。让我们把程序复杂一点,就能看到了。 对于复数,通常会有另外一种表达方式叫做基于极坐标系的极坐标表示。跟用复数域上的点的特定位置表示实部虚部不同,极坐标系中用离开原点的距离(或模)和偏离原点的方向(或角度)来表示。 下图表示两个坐标系系统。 在极坐标系中,复数记作reiθ ,其中r是模(半径),θ是用弧度表示的角度。 幸运的是,很容易从两个坐标系中进行转换。 从笛卡尔到极坐标系: r = x2 + y2 θ = arctan(y/x) 从极坐标系到笛卡尔坐标系: x = r cos θ y = r sin θ 那么我们应该使用哪一种表达方式呢?因为有些操作在笛卡尔坐标系中简单些,如加法;而另一些操作在极坐标系中简单些,如乘法。所以一个办法是我们写一个使用两种表达方式的类,让他们根据需要可以自动转换。 ~~~ class Complex { double real, imag; double mag, theta; bool cartesian, polar; public: Complex () { cartesian = false; polar = false; } Complex (double r, double i) { real = r; imag = i; cartesian = true; polar = false; } }; ~~~ 在这个类中有6个变量,这就意味着这样会比之前的任何一种占用的空间都要多。不过我们很快就会看到这样做是很有用的。 其中四个变量可以根据名字判断他们的意思,分别是一个复数的实部,虚部,角度,半径。另外两个变量cartesian和polar则是表示对应坐标系的值是否有效的标志。 举例来说,啥都不做的这个构造函数将两个标志量设置为false表明该对象无论哪种表达方式,都还不是有效的复数。 第二个构造函数使用参数来初始化实部和虚部,但不会计算模或角度。并会把极坐标的标志位置为false来警告其他函数不应当访问模或角度值,直到他们被设置为正确的值。 现在应该清楚为何将变量置为私有了吧。如果一个客户程序被允许不受限制的访问,读取了未初始化的值就很容易导致出错。在下一部分,我们将添加一些访问函数来避免这种错误。