摘要:本示例程序出自Bill Wagner 《c#小黑书》,这是本很出名的C#方面的经典图书。
这个简单的例子完成一些简单的物理计算,是关于计算重力加速度,距离和速度之间的关系的.例子虽然简单,却演示了很多知识点儿,枚举,类,静态方法,switch语句,常量,只读域,重载的构造函数,控制台输出等.此外还演示了一个物理规律,复习了一下初中物理知识.其次看一下代码的的命名方式等,养成良好的代码写作习惯.关于这本书的源码,我会陆续的翻译过来的,其中可以挖掘好多开发技巧,我想先从简单的开始,不放过每一个知识点儿,这样翻译完的话也许c#水平和英语就提高一些了。
关于作者:
Bill Wagner 是SRT Solutions的创始人和顾问,专门研究.NET 开发。他是The C# Core Language Little Black Book一书的作者。 十多年来,他一直从事软件开发与教学工作。他是Visual Studio Magazine的专栏作家,并在许多关于改进软件开发习惯的会议上做演讲。他从事的软件程序的范围很广,从儿童游戏到生物信息学研究。联系方式:wwagner@SRTsolutions.com。
Bill Wagner 是个非常了不起的人,我昨天看的那篇文章就是他写的,我从网上搜索到了他的博客
http://www.srtsolutions.com/public/blog/20574
还有他写的c#小黑书的源码
http://www.srtsolutions.com/public/blog/75433
namespace CSharpLittleBlackBook.Chapter3
{
//引用命名空间,c#里的using关键字有好多种用法,
//这里是用来引入命名空间的.
using System;
/// <summary>
/// 这个简单的例子完成一些简单的物理计算,是关于计算重力加速度,距离和速度之间的关系的.
/// 例子虽然简单,却演示了很多知识点儿,枚举,类,静态方法,switch语句,常量,只读域,重载的构造函数,控制台输出等.
/// 此外还演示了一个物理规律,复习了一下初中物理知识.其次看一下代码的的命名方式等,养成良好的代码写作习惯.
/// </summary>
/// <remarks>
/// 这个类有两个构造函数,第一个构造函数创建一个默认重力加速度的值,
/// 你也可以在另一个构造函数里指定加速度的值,
/// 一旦创建了对象,公用的方法将能返回一个物体指定时间落到地面所经过的距离和最后的速度.
/// </remarks>
public class DistanceCalculator
{
/// <summary>
/// 这个距离单位枚举描述不同的距离度量单位.
/// </summary>
public enum DistanceUnits
{
inches, //英寸
feet, //英尺
yards, //码
miles //英里
}
//定义默认重力加速度,常量用大写字母表示.
public const double GRAVITY = 32;
//定义英尺和其它长度度量单位之间的换算
private const double FEET_PER_INCH = 1.0 / 12.0; //定义英尺和英寸的换算比例,一英尺等于12英寸
private const double FEET_PER_YARD = 3.0; //3英尺一码
private const double FEET_PER_MILE = 5280.0; //5280英尺等于一盈利
//定义一个只读域,只读域不同于常量的地方是,它可以在构造函数里初始化,一旦初始化后就不能更改.
private readonly double accel;
/// <summary>
/// 默认构造函数,不过这里的this是干什么的呀,后来想了想,这段代码相当于,就是这个默认构造调用重载的构造
/// public DistanceCalculator ()
///{
/// this (GRAVITY);
///}
/// </summary>
public DistanceCalculator () :
this (GRAVITY)
{
}
/// <summary>
/// 重载的构造函数,定义一个重力加速度值
/// </summary>
/// <param name="a">加速度值</param>
public DistanceCalculator(double a)
{
accel = a;
//
// TODO: 在这里添加构造函数的业务逻辑代码
//
}
/// <summary>
/// 定义加速度属性,属性是只读的,属性的值在构造函数里初始化的.
/// </summary>
public double Acceleration
{
get
{
return accel;
}
}
/// <summary>
/// 获取距离,重力加速度乘以时间的平方就是总的经过的距离.
/// 按微软的推荐,方法应该用pacal大小写来命名,就是组成标识符的每个单词的手写字母大写,
/// 这里的做法并没有按照微软的推荐来命名方法.
/// 然后调用自定义函数convert来转换成相应的度量单位的值.
/// convert是一个私有静态方法,在这里可以直接调用.
/// </summary>
/// <param name="time">时间</param>
/// <param name="measurement">单位</param>
/// <returns>距离</returns>
public double getDistance (double time, DistanceUnits measurement)
{
double f = accel * time * time;
return convert (f, measurement); //调用convert把距离转换成适当的度量单位的值
}
/// <summary>
/// 获取最后的速度,如果一个物体是从高处往下落,刚开始速度为0,落下的时候速度越来越大,这里获取最后的速度.
/// 这个最终速度是加速度乘以物体落下的时间来获得的,初中物理学过的.
/// </summary>
/// <param name="time">物体落下的时间段儿</param>
/// <param name="measurement">返回的距离度量单位</param>
/// <returns>返回物体最后的速度</returns>
public double getVelocity (double time, DistanceUnits measurement)
{
double f = accel * time;
return convert (f, measurement);
}
/// <summary>
/// 这个定义的是一个私有的静态方法,记住静态方法只能使用类的静态成员,
/// 而它本身既可以由静态成员使用,也可以由非静态成员使用.
/// </summary>
/// <param name="ft">输入原始的double的值</param>
/// <param name="measurement">要转换的长度度量单位</param>
/// <returns>返回用指定度量单位表示的距离</returns>
static private double convert (double ft, DistanceUnits measurement)
{
double distance; //声明私有双精度变量,写程序的时候要善于利用一些临时变量.
//利用开关语句来分别处理传入的枚举值,switch要求判断的表达式的值是整型或者字符串.
//而枚举的值实际上默认就是整形的,所以这里不经过转换就可以直接使用开关语句来处理.
//与 C++ switch 语句不同,C# 不支持从一个 case 标签显式贯穿到另一个 case 标签.
//但是如果上一个case语句什么也不做的话,这两个case语句可以公用一个执行部分的语句.
//如果switch的表达式语句和所有的case值都不匹配就会执行default标签后的代码部分.
switch (measurement)
{
case DistanceUnits.inches:
distance = ft / FEET_PER_INCH; //利用英尺和其它长度单位的比例来计算出返回值.
break;
case DistanceUnits.feet:
distance = ft;
break;
case DistanceUnits.yards:
distance = ft / FEET_PER_YARD;
break;
case DistanceUnits.miles:
distance = ft / FEET_PER_MILE;
break;
default:
distance = 0;
break;
}
return distance;
}
/// <summary>
/// 这是程序的主入口,c#程序都要有一个Main()函数才能运行.
/// </summary>
public static void Main ()
{
DistanceCalculator d = new DistanceCalculator(); //实例化一个DistanceCalculator类d.
double dist = d.getDistance(10, DistanceUnits.feet); //调用getDistance方法来获取物体掉落10秒钟所经过的高度.
System.Console.WriteLine("Distance after 10 sec: {0} feet", dist); //从控制台输出值,Console.WriteLine有很多重载版本,并且输出值后换行.
double v = d.getVelocity (10, DistanceUnits.feet); //调用getVelocity方法来获取物体掉落10秒钟后最终的速度.
System.Console.WriteLine("Velocity after 10 sec: {0} feet / sec", v);
}
}
}
{
//引用命名空间,c#里的using关键字有好多种用法,
//这里是用来引入命名空间的.
using System;
/// <summary>
/// 这个简单的例子完成一些简单的物理计算,是关于计算重力加速度,距离和速度之间的关系的.
/// 例子虽然简单,却演示了很多知识点儿,枚举,类,静态方法,switch语句,常量,只读域,重载的构造函数,控制台输出等.
/// 此外还演示了一个物理规律,复习了一下初中物理知识.其次看一下代码的的命名方式等,养成良好的代码写作习惯.
/// </summary>
/// <remarks>
/// 这个类有两个构造函数,第一个构造函数创建一个默认重力加速度的值,
/// 你也可以在另一个构造函数里指定加速度的值,
/// 一旦创建了对象,公用的方法将能返回一个物体指定时间落到地面所经过的距离和最后的速度.
/// </remarks>
public class DistanceCalculator
{
/// <summary>
/// 这个距离单位枚举描述不同的距离度量单位.
/// </summary>
public enum DistanceUnits
{
inches, //英寸
feet, //英尺
yards, //码
miles //英里
}
//定义默认重力加速度,常量用大写字母表示.
public const double GRAVITY = 32;
//定义英尺和其它长度度量单位之间的换算
private const double FEET_PER_INCH = 1.0 / 12.0; //定义英尺和英寸的换算比例,一英尺等于12英寸
private const double FEET_PER_YARD = 3.0; //3英尺一码
private const double FEET_PER_MILE = 5280.0; //5280英尺等于一盈利
//定义一个只读域,只读域不同于常量的地方是,它可以在构造函数里初始化,一旦初始化后就不能更改.
private readonly double accel;
/// <summary>
/// 默认构造函数,不过这里的this是干什么的呀,后来想了想,这段代码相当于,就是这个默认构造调用重载的构造
/// public DistanceCalculator ()
///{
/// this (GRAVITY);
///}
/// </summary>
public DistanceCalculator () :
this (GRAVITY)
{
}
/// <summary>
/// 重载的构造函数,定义一个重力加速度值
/// </summary>
/// <param name="a">加速度值</param>
public DistanceCalculator(double a)
{
accel = a;
//
// TODO: 在这里添加构造函数的业务逻辑代码
//
}
/// <summary>
/// 定义加速度属性,属性是只读的,属性的值在构造函数里初始化的.
/// </summary>
public double Acceleration
{
get
{
return accel;
}
}
/// <summary>
/// 获取距离,重力加速度乘以时间的平方就是总的经过的距离.
/// 按微软的推荐,方法应该用pacal大小写来命名,就是组成标识符的每个单词的手写字母大写,
/// 这里的做法并没有按照微软的推荐来命名方法.
/// 然后调用自定义函数convert来转换成相应的度量单位的值.
/// convert是一个私有静态方法,在这里可以直接调用.
/// </summary>
/// <param name="time">时间</param>
/// <param name="measurement">单位</param>
/// <returns>距离</returns>
public double getDistance (double time, DistanceUnits measurement)
{
double f = accel * time * time;
return convert (f, measurement); //调用convert把距离转换成适当的度量单位的值
}
/// <summary>
/// 获取最后的速度,如果一个物体是从高处往下落,刚开始速度为0,落下的时候速度越来越大,这里获取最后的速度.
/// 这个最终速度是加速度乘以物体落下的时间来获得的,初中物理学过的.
/// </summary>
/// <param name="time">物体落下的时间段儿</param>
/// <param name="measurement">返回的距离度量单位</param>
/// <returns>返回物体最后的速度</returns>
public double getVelocity (double time, DistanceUnits measurement)
{
double f = accel * time;
return convert (f, measurement);
}
/// <summary>
/// 这个定义的是一个私有的静态方法,记住静态方法只能使用类的静态成员,
/// 而它本身既可以由静态成员使用,也可以由非静态成员使用.
/// </summary>
/// <param name="ft">输入原始的double的值</param>
/// <param name="measurement">要转换的长度度量单位</param>
/// <returns>返回用指定度量单位表示的距离</returns>
static private double convert (double ft, DistanceUnits measurement)
{
double distance; //声明私有双精度变量,写程序的时候要善于利用一些临时变量.
//利用开关语句来分别处理传入的枚举值,switch要求判断的表达式的值是整型或者字符串.
//而枚举的值实际上默认就是整形的,所以这里不经过转换就可以直接使用开关语句来处理.
//与 C++ switch 语句不同,C# 不支持从一个 case 标签显式贯穿到另一个 case 标签.
//但是如果上一个case语句什么也不做的话,这两个case语句可以公用一个执行部分的语句.
//如果switch的表达式语句和所有的case值都不匹配就会执行default标签后的代码部分.
switch (measurement)
{
case DistanceUnits.inches:
distance = ft / FEET_PER_INCH; //利用英尺和其它长度单位的比例来计算出返回值.
break;
case DistanceUnits.feet:
distance = ft;
break;
case DistanceUnits.yards:
distance = ft / FEET_PER_YARD;
break;
case DistanceUnits.miles:
distance = ft / FEET_PER_MILE;
break;
default:
distance = 0;
break;
}
return distance;
}
/// <summary>
/// 这是程序的主入口,c#程序都要有一个Main()函数才能运行.
/// </summary>
public static void Main ()
{
DistanceCalculator d = new DistanceCalculator(); //实例化一个DistanceCalculator类d.
double dist = d.getDistance(10, DistanceUnits.feet); //调用getDistance方法来获取物体掉落10秒钟所经过的高度.
System.Console.WriteLine("Distance after 10 sec: {0} feet", dist); //从控制台输出值,Console.WriteLine有很多重载版本,并且输出值后换行.
double v = d.getVelocity (10, DistanceUnits.feet); //调用getVelocity方法来获取物体掉落10秒钟后最终的速度.
System.Console.WriteLine("Velocity after 10 sec: {0} feet / sec", v);
}
}
}