数据类型、表达式和语句
大约 6 分钟
数据类型、表达式和语句
变量
- 类型推断:var 关键字
- 常量:const 关键字
- 不能从变量中提取值来初始化常量
- 常量总是隐式静态的
数据类型
C# 预定义类型
非简单类型(3种)
object
所有其他类型的基类string
多个或零个Unicode字符所组成的序列dynamic
动态语言编写的程序集时使用
简单类型(13种)
名称 .Net 框架类型 含义 sbyte System.SByte 8位有符号整数 byte System.Byte 8位无符号整数 short System.Int16 16位有符号整数 ushort System.UInt16 16位无符号整数 int System.Int32 32位有符号整数 uint System.UInt32 32位无符号整数 long System.Int64 64位有符号整数 ulong System.UInt64 64位无符号整数 float System.Single 单精度浮点数 double System.Double 双精度浮点数 bool System.Boolean 布尔 char System.Char Unicode 字符 decimal System.Decimal 小数类型的有效数字精度位28位
用户自定义类型
- 类class、结构struct、数组array、枚举enum、委托delegate、接口interface
值类型和引用类型
引用类型:object 、string 、dynamic 、class 、interface 、delegate 、array
值类型:简单类型 、结构 、枚举
决定了数据在内存中的存储位置(堆或栈)
引用类型的成员数据始终存储在堆,堆地址存在于栈中
字面量 literal
后缀 | 类型 | |
---|---|---|
整数 | 无 | int、uint、long、ulong |
U | uint、ulong | |
L | long、ulong | |
UL | ulong | |
实数 | 无 | double |
F | float | |
D | double | |
M | decimal | |
字符 | 单个字符 | |
简单转义序列 | \t | |
十六制转义序列 | \x0009 | |
**Unicod转义序列 ** | \u0009 | |
字符串 | @” “ | 逐字字符串,不进行转义,连续””表示单个” |
静态类型和 dynamic 关键字
- 静态类型:变量的类型决定了其在运行时需要的内存大小及存储在堆或栈上,变量在编译时确定去类型并且在运行时不能再更改。
- dynamic 类型:编译时不进行解析并将与之关联的数据一并打包,待运行是解析其类型并进行数据类型一致性检查。
栈和堆
栈
- LIFO(Last-In First-Out),后进先出的内存数组
- 数据只能从栈顶插入或删除(入栈push或出栈pop)
堆
- 一块内存区域
- 数据能够以任意顺序存入或移除
- 堆中的无主数据由GC(Garbage Collector垃圾收集器)自动清除
数据转换
隐式转换
- 自动转换,没有精度丢失,短类型转长类型;
- 零扩展:用 0 填充多出来的高位;
- 符号扩展:对有符号类型,用符号填充多出来的高位;
显示转换和强制转换
- 长类型转短类型,数据可能会有溢出;
- ( 目标类型 ) 源表达式 ;
装箱/拆箱
- 任何值在object或System.ValueType之间装换
用户自定义转换
- 关键字:implicit 隐式转换,explicit 显示转换;
- 只能定义类或结构,不能重定义标准隐式转换或显式转换;
- 源类型和目标类型必须是不同类型且没有继承关系;
public static [implicit|explicit] operator TargetType(SourceType Identifier)
{
...
return ObjectOfTargetType
}
Parse把字符串解析为数据值
所有预定于的简单类型都有一个 Parse 静态方法把这个类型的字符串值转换成类型的实际值;
double d = double.Parse ( “3.14”);
转换失败则会抛出异常
TryParse方法能够避免抛出异常,返回是否转换成功bool值;
string isSuccess = double.TryParse ( “3.14”,out double result) ? “Yes” : ”No”;
可空类型
可空类型允许将值类型标记为null;
不能从引用类型创建可空类型;
不能显示声明可空类型,编译器会使用泛型隐式创建可空类型;
int? varName = 10 ; //使用C#快捷语法声明(推荐) Nullable<MyStruct> varName = new Nullable<MyStruct>(); //使用泛型语法声明
可空类型结构
- HasValue:只读的bool属性;
- Value:返回基础类型值的只读属性;
- 预定义简单值类型可直接使用可空变量访问值;
- 可空自定义值类型值的访问需要使用可空类型的Value属性,然后使用自定义值类型的属性名来访问某个属性的值:
varName.Value.PropertyName;
赋值
非可空值类型可以隐式转换成对应的可空类型;
可空类型需要显式转换成对应的非可空之类型;
int? a = 5; int b = (int) a; //显示转换 int a = 5; int? b = a; //隐式转换
??空接合运算符
- 允许在可空类型变量为null时返回一个值给表达式;
- 可空类型变量 ?? 对应非可空值
- 如果可空变量为空,则返回对应非可空值,否则返回可空类型变量值
- 其他:两个null可空类型变量相等
运算符
运算符优先级(从高到低)
运算符结合性(同等优先级是操作顺序)
- 右结合:赋值运算符、条件运算符
- 左结合:其他二元运算符
自增、自减运算符
- 前置递增、前置递减:先进行自增自减,再参与运算
- 后置递增、后置递减:先进行参与运算,再自增自减
逻辑运算符
- 逻辑运算符是短路操作
条件运算符
condition ? expr1 : expr2 ;
如果 condition 为 true 则返回 expr1 的值,否则返回 expr2 的值
运算符重载
public static TypeName operator + ( type1 para1, type2 para2 ){ … }
- ++、-- 重载后前置和后置没有区别
条件语句
if
- if
- if ... else ...
- if ... else if ... else
switch
标签必须为常量表达式
switch(testExpr) { case ConstExpr1: // 分支 1 ... break; ... case ConstExprN: // 分支 N ... break; default: // 默认分支 ... break; }
循环语句
while 、do...while
while(testExpr)
{
...
}
do
{
...
}while(testExpr)
for
for(initializer;TestExpr;IterationExpr)
{
...
}
// 多个表达式用逗号分隔
跳转语句
break:跳出最内层循环
Continue:跳过本层循环,直接进入下一次循环
goto、标签
跳转到 indentifier 标记的位置
goto indentifier;
indentifier:Statement;
using 语句
有助于简化对某些类型的非托管对象有数量限制或很耗费系统资源的使用后的资源释放。
能够防止运行错误后资源得不到处置。
using 其本质相当于
try{ ... } finally{ Resource.Dispose;}
// 语法 using(ResouceType Indentifier = Exprssion) { ... } // 示例:读写资源 // 用 using 语句后即使不用调用 tw.Close() 也能自动释放资源,不会在上下文中造成读写冲突 using ( TextWriter tw = File.CreateText ( “LinColn.txt”)) { tw.WriteLine ( “Four score and seven years age…” ); }
using 可以用于同类型多个资源和嵌套
using ( TextWriter tw1 = File.CreateText ( “LinColn.txt”) tw2 = File.CreateText ( “Flanklin.txt”)) { tw1.WriteLine ( “Four score and seven years age…” ); tw2.WriteLine ( “Early to bed ...” ); } using ( TextWriter tw1 = File.CreateText ( “LinColn.txt”)) { tw1.WriteLine ( “Four score and seven years age…” ); using ( TextWriter tw2 = File.CreateText ( “Flanklin.txt”)) { tw2.WriteLine ( “Early to bed ...” ); } }
其它语句
语句 | 描述 |
---|---|
checked、unchecked | 控制溢出检查上下文 |
foreach | 遍历一个集合的每个成员 |
try...throw...finally... | 异常捕获 |
return | 返回一个值 |
yield | 迭代 |