编写高质量代码改善C#程序的157个建议——建议2: 使用默认转型方法
建议2: 使用默认转型方法
除了字符串操作外,程序员普遍会遇到的第二个问题是:如何正确地对类型实现转型。在上一个建议中,从int转型为string,我们使用了类型int的ToString方法。在大部分情况下,当需要对FCL提供的类型进行转型时,都应该使用FCL提供的转型方法。
这些转型方法包括:
使用类型的转换运算符。
使用类型内置的Parse、TryParse,或者如ToString、ToDouble和ToDateTime等方法。
使用帮助类提供的方法。
使用CLR支持的转型。
下面分别对这些方法进行说明。
1. 使用类型的转换运算符
使用类型的转换运算符,其实就是使用类型内部的一个方法(即函数)。转换运算符分为两类:隐式转换和显式转换(强制转换)。基元类型普遍都提供了转换运算符,如:
int i = ;
float j = ;
j = i; //int到float(Single)存在一个隐式转换
i = (int)j; //float(Single)到int存在,而且必须存在一个显式转换
注意 所谓“基元类型”,是指编译器直接支持的数据类型,即直接映射到FCL中的类型。基元类型包括sbyte、byte、short、 ushort、int、uint、long、ulong、char、float、double、bool、decimal、object、string。
用户自定义的类型也可以通过重载转换运算符的方式来提供这一类转换,代码如下所示:
class Program
{
static void Main(string[] args)
{
Ip ip = "192.168.0.96";
Console.WriteLine(ip.ToString());
}
} class Ip
{
IPAddress value; public Ip(string ip)
{
value = IPAddress.Parse(ip);
}
public static implicit operator Ip(string ip)
{
Ip iptemp = new Ip(ip);
return iptemp;
} public override string ToString()
{
return value.ToString();
}
}
在上面的代码中:
- Ip ip = "192.168.0.96";
提供的就是字符串到类型Ip之间的隐式转换。但是,除非考虑一些初始化值,一般不建议用户对自己的类型重载转换运算符。如果用户自定义的类型之间需要转换,建议从面向对象的角度考虑,因为它们一般都含有某种关系(如继承、实现等)。在这种情况下,就应该使用即将介绍的第四种方法:CLR支持的转型。 不过,我们仍需掌握FCL中的类型,尤其是基元类型之间的转换运算符,以便快速地在基元类型间进行转换。
2. 使用类型内置的Parse、TryParse,或者如ToString、ToDouble、ToDateTime等方法
在FCL中,如果某个类型经常需要进行转型操作,类型自身则会带有一些转型方法。比如从string转型为int,因为其经常发生,所以int本身就提供了Parse和TryParse方法。一般情况下,如果要对某类型进行转型操作,建议先查阅该类型的API文档。
3. 使用帮助类提供的方法
可以使用如System.Convert类、System.BitConverter类来进行类型的转换。
System.Convert提供了将一个基元类型转换为其他基元类型的方法,如ToChar、ToBoolean方法等。值得注意的 是,System.Convert还支持将任何自定义类型转换为任何基元类型,只要自定义类型继承了IConvertible接口就可以。如上文中的Ip 类,如果将Ip转型为string,除了重写Object的ToString方法外,还可以实现IConvertible的ToString方法,代码如 下所示:
- class Ip : IConvertible
- {
- //省略
- public bool ToBoolean(IFormatProvider provider)
- {
- throw new InvalidCastException("Ip-to-Boolean conversion is not supported.");
- }
- public string ToString(IFormatProvider provider)
- {
- return value.ToString();
- }
- //省略
- }
继承IConvertible接口必须同时实现其他转型方法,如上文中的ToBoolean,如果不支持此类转型,则应该抛出一个InvalidCastException,而不是一个NotImplementedException。
System.BitConverter提供了基元类型与字节数组之间相互转换的方法,这里不再赘述。
4. 使用CLR支持的转型
CLR支持的转型,即上溯转型和下溯转型。这个概念首先是在Java中提出来的,实际上就是基类和子类之间的相互转换,如图1-1所示。
在进行子类向基类转型的时候支持隐式转换,如Dog显然就是一个Animal;而当Animal转型为Dog的时候,必须是显式转换,因为Animal还可能是一个Cat,代码如下所示:
Animal animal;
Dog dog = new Dog();
animal = dog; //隐式转换,因为Dog就是Animal
//dog = animal; //编译不通过
dog = (Dog)animal; //必须存在一个显式转换
转自:《编写高质量代码改善C#程序的157个建议》陆敏技
编写高质量代码改善C#程序的157个建议——建议2: 使用默认转型方法的更多相关文章
- 编写高质量代码改善C#程序的157个建议[1-3]
原文:编写高质量代码改善C#程序的157个建议[1-3] 前言 本文主要来学习记录前三个建议. 建议1.正确操作字符串 建议2.使用默认转型方法 建议3.区别对待强制转换与as和is 其中有很多需要理 ...
- 读书--编写高质量代码 改善C#程序的157个建议
最近读了陆敏技写的一本书<<编写高质量代码 改善C#程序的157个建议>>书写的很好.我还看了他的博客http://www.cnblogs.com/luminji . 前面部 ...
- 编写高质量代码改善C#程序的157个建议——建议157:从写第一个界面开始,就进行自动化测试
建议157:从写第一个界面开始,就进行自动化测试 如果说单元测试是白盒测试,那么自动化测试就是黑盒测试.黑盒测试要求捕捉界面上的控件句柄,并对其进行编码,以达到模拟人工操作的目的.具体的自动化测试请学 ...
- 编写高质量代码改善C#程序的157个建议——建议156:利用特性为应用程序提供多个版本
建议156:利用特性为应用程序提供多个版本 基于如下理由,需要为应用程序提供多个版本: 应用程序有体验版和完整功能版. 应用程序在迭代过程中需要屏蔽一些不成熟的功能. 假设我们的应用程序共有两类功能: ...
- 编写高质量代码改善C#程序的157个建议——建议155:随生产代码一起提交单元测试代码
建议155:随生产代码一起提交单元测试代码 首先提出一个问题:我们害怕修改代码吗?是否曾经无数次面对乱糟糟的代码,下决心进行重构,然后在一个月后的某个周一,却收到来自测试版的报告:新的版本,没有之前的 ...
- 编写高质量代码改善C#程序的157个建议——建议154:不要过度设计,在敏捷中体会重构的乐趣
建议154:不要过度设计,在敏捷中体会重构的乐趣 有时候,我们不得不随时更改软件的设计: 如果项目是针对某个大型机构的,不同级别的软件使用者,会提出不同的需求,或者随着关键岗位人员的更替,需求也会随个 ...
- 编写高质量代码改善C#程序的157个建议——建议153:若抛出异常,则必须要注释
建议153:若抛出异常,则必须要注释 有一种必须加注释的场景,即使异常.如果API抛出异常,则必须给出注释.调用者必须通过注释才能知道如何处理那些专有的异常.通常,即便良好的命名也不可能告诉我们方法会 ...
- 编写高质量代码改善C#程序的157个建议——建议152:最少,甚至是不要注释
建议152:最少,甚至是不要注释 以往,我们在代码中不写上几行注释,就会被认为是钟不负责任的态度.现在,这种观点正在改变.试想,如果我们所有的命名全部采用有意义的单词或词组,注释还有多少存在的价值. ...
- 编写高质量代码改善C#程序的157个建议——建议151:使用事件访问器替换公开的事件成员变量
建议151:使用事件访问器替换公开的事件成员变量 事件访问器包含两部分内容:添加访问器和删除访问器.如果涉及公开的事件字段,应该始终使用事件访问器.代码如下所示: class SampleClass ...
- 编写高质量代码改善C#程序的157个建议——建议150:使用匿名方法、Lambda表达式代替方法
建议150:使用匿名方法.Lambda表达式代替方法 方法体如果过小(如小于3行),专门为此定义一个方法就会显得过于繁琐.比如: static void SampeMethod() { List< ...
随机推荐
- centos7防火墙 启动和关闭
CentOS 7.0默认使用的是firewall作为防火墙,这里改为iptables防火墙.firewall:systemctl start firewalld.service #启动firewa ...
- 文化之旅(dijstra)
2012_p4 文化之旅 (culture.cpp/c/pas) 时间限制: 1 Sec 内存限制: 128 MB提交: 43 解决: 16[提交][状态][讨论版][命题人:外部导入] 题目描述 ...
- Java-Runoob:Java 运算符
ylbtech-Java-Runoob:Java 运算符 1.返回顶部 1. Java 运算符 计算机的最基本用途之一就是执行数学运算,作为一门计算机语言,Java也提供了一套丰富的运算符来操纵变量. ...
- 讲解一下this (作用域)
this的指向:普通函数内的this指向全局变量 构造函数内部this指向新创建出来的对象 对象方法内的this指向的是调用该方法的对象 call,apply,bind可以改变this的指向
- SVN安装和使用总结
SVN简介: 为什么要使用SVN? 程序员在编写程序的过程中,每个程序员都会生成很多不同的版本,这就需要程序员有效的管理代码,在需要的时候可以迅速,准确取出相应的版本. Subversion是什么? ...
- 1 响应式页面-@media介绍,
我们为什么要写自适应的页面(响应式页面) 众所周知,电脑.平板.手机的屏幕是差距很大的,假如在电脑上写好了一个页面,在电脑上看起来不错,但是如果放到手机上的话,那可能就会乱的一塌糊涂,这时候怎么解决呢 ...
- VMWARE三种网络配置
由于linux目前很热门,越来越多的人在学习linux,但是买一台服务放家里来学习,实在是很浪费.那么如何解决这个问题?虚拟机软件是很好的选择,常用的虚拟机软件有vmware workstations ...
- openark对MySQL进行Online_DDL
1.用oak对表sbtest1做添加字段和增加索引的Online DDL openark kit 提供一组小程序,用来帮助日常的 MySQL 维护任务,可代替繁杂的手工操作. 包括: oak-appl ...
- Win10系统windows mobile设备中心无法连接WinCE采集器
1.开始-->运行,输入services.msc回车 2.在打开的服务界面中,找到“基于Windows Mobile 2003的连接设备” 3.右击属性,修改成自动 4.点击登陆选项卡,选择本地 ...
- 一个简单的AXIS远程调用Web Service示例
我们通常都将编写好的Web Service发布在Tomcat或者其他应用服务器上,然后通过浏览器调用该Web Service,返回规范的XML文件.但是如果我们不通过浏览器调用,而是通过客户端程序调用 ...