深入.NET平台和C#编程 第三章 学习笔记

 

深入.NET平台和C#编程
第三章  用对象思考:值类型和引用类型
【常量】
有些值在程序的整个过程都不会发生变化 ,我们可以把它定义成常量.
 
常量定义关键字 :const
例 :
public class Compute
    {
        const double Pi = 3.14;
        // 计算圆的周长
        public double Perimeter(double radius)
        {
            Pi = 3.1415;
            return 2 * Pi * radius;
        }
        // 计算圆的面积
        public double Area(double radius)
        {
            return Pi * radius * radius;
        }
    }
 
【枚举】
使用枚举可以避免不合理的赋值 .
例如我们定义一个性别 (string)属性,我们知道这个属性只能接受两个有效值:男和女,如果要其他string类型的值赋给它,编译器也会通过.
 
枚举定义关键字 :enum
例 :
public enum Genders
{
    Male, Female
}
 
class Student
{
    ///<summary>
    /// 性别
    ///</summary>
    private Genders gender;
    public Genders Gender
    {
        get { return gender; }
        set { gender = value; }
    }
}
 
class Program
{
    static void Main(string[] args)
    {
        // 使用枚举赋值
        Student stu = new Student();
        stu.Gender = Genders.Male;
        stu.Gender = Genders.Female;
        stu.Gender = " 外星人" ; // 编译错误
    }
}
 
 
枚举还可以用描述性的名称表示整数值
public enum Genders
{
    Male = 0, Female = 1
}
将枚举的值转换成int型,就可以得到定义枚举时所指定的整数值:
int genderNum = (int)stu.Gender;
 
在程序中还可以获得它的字符串表示:
Console .WriteLine(" 您输入的是性别是{0}" , stu.Gender.ToString());
 
还可以从一个字符串中获取枚举值:
stu.Gender = (Genders)(Enum.Parse(typeof(Genders), "Female"));
Console .WriteLine(" 您输入的是性别是{0}" , stu.Gender.ToString());
Enum.Parse 方法,第一个参数是关键字typeof(EnumType,”string”),最后使用枚举类型强制转换.
 
 
【问题】
枚举的主体中定义属性和方法? 不可以
 
 
【结构】
结构和类很相似 ,在使用结构时,可以不用NEW,直接定义就可以了,但是必须为结构成员赋初值.定义结构的关键字:struct
 
struct StructStudent
{
    public string Name;
    public Genders Gender;
    public int Age;
    public string Hobby;
    public int Popularity;
 
    public void SayHi()
    {
        string message;
 
        message = string.Format(
            " 大家好,我是{0} 同学,今年{1} 岁了,我喜欢{2}。我的人气值高达{3} !" ,
            this.Name, this.Age, this.Hobby, this.Popularity
        );
 
        MessageBox.Show(message);
    }
}
 
结构可以有重载有参的构造函数 (C#总是提供结构一个无参的构造函数,所以我们使用结构时不用new):
 
struct StructStudent
{
    public string Name;
    public Genders Gender;
    public int Age;
   public string Hobby;
    public int Popularity;
 
    public StructStudent(string name, Genders gender, int age, string hobby, int popularity)
    {
        this.Name = name;
        this.Gender = gender;
        this.Age = age;
        this.Hobby = hobby;
        this.Popularity = popularity;
    }
 
    public void SayHi()
    {
        string message;
 
        message = string.Format(
            " 大家好,我是{0} 同学,今年{1} 岁了,我喜欢{2}。我的人气值高达{3} !" ,
            this.Name, this.Age, this.Hobby, this.Popularity
        );
 
        MessageBox.Show(message);
    }
}
 
类和结构的差别 :
 
 
 
理解C#中的值类型和引用类型:值类型与引用类型在内存中存储的方式不同
 
【值类型】
// 使用值类型 student结构
StructStudent student1 = new StructStudent();
StructStudent student2 = new StructStudent();
student1.Age = 18;
student2 = student1;
student2.Age = 20;
Console .WriteLine("student1 = {0},student2 = {1}", student1.Age, student2.Age);
 
结果 : student1.Age = 18 , student2.Age = 20
 
※当student1赋值给student2时, student2对象会保存为student1的值.
student2 的Age赋值20时,就会在student2的区域内存保存Age= 20.
 
【引用类型】
// 使用引用类型 student类
Student student1 = new Student();
Student student2 = new Student();
student1.Age = 18;
student2 = student1;
student2.Age = 20;
Console .WriteLine("student1 = {0},student2 = {1}", student1.Age, student2.Age);
 
结果:student1.Age = 20 , student2.Age = 20
 
 
※当student1的Age赋值18时,就会在student1的区域内存保存Age= 18.
※将student1赋值给student2时,它们同时引用同一对象, student2的值会保存为student1的值.
※当student2的Age赋值20时,由于它们两个都引用同一对象,所以它们的值都会发生变化.
 
【装箱与拆箱】
值类型和引用类型可以相互转换,值类型转换为引用类型称为”装箱”,反之称之为”拆箱”.
static void Main(string[] args)
{
    int i = 123;
object o = i; // 隐式装箱
// 转换为值类型时,所定义的值类型数据与引用类型的数据类型要一致,如果类型错误,会发生异常
// 所以拆箱要注意异常处理
    try
    {
        int j = (int)o; // 拆箱
        System.Console.WriteLine(" 取消装箱成功." );
    }
    catch (System.InvalidCastException e)
    {
        System.Console.WriteLine("{0} 错误: 不正确的取消装箱." , e.Message);
    }
}
 
【不同类型的参数传递】
值方式参数传递: 参数是值类型,参数值不会被修改, 参数是引用类型,参数值会被修改.
引用方式参数传递: 参数是值类型/引用类型,参数值都会被修改.
 
【索引器】
定义一个索引器要使用关键字:this
可以通过重载索引器,从而自定义它的访问方式
public student_my this[int index]
{
      get { return myStu[index]; }
}
索引器实例: 我们定义三个类,学生类,班级类,索引器
 
/// 学生类 /
using System.Windows.Forms;
namespace MySchool
{
    ///<summary>
    /// 学员类
    ///</summary>
    class student_my
    {
        // 建立构造函数及方法重载
        public student_my():this("student_x",18) { }
        public student_my(string name):this(name,18) { }
        public student_my(string name, int age)
        {
            this.name = name;
            this.age = age;
        }
 
        ///<summary>
        /// 学生姓名
        ///</summary>
        private string name;
        public string Name
        {
            get { return name; }
            set { name = value; }
        }
 
        ///<summary>
        /// 学员年龄
        ///</summary>
        private int age;
        public int Age
        {
            get { return age; }
            set
            {
               if (age > 1 || age < 100)
                {
                    age = value;
                }
                else
                {
                    age = 18;
                }
            }
        }
        ///<summary>
        /// 自我介绍方法
        ///</summary>
        public void SayHi()
        {
            string hi = string.Format(" 大家好!我叫{0},我今年{1}岁" ,name,age);
            MessageBox.Show(hi);
        }
    }
}
 
 
 
 
/// 班级类 /
namespace MySchool
{
    ///<summary>
    /// 班级类
    ///</summary>
    class Class_my
    {
        public Class_my(string name)
        {
            this.Class_name = name;
            this.stuIndex = new student_index();
        }
 
        ///<summary>
        /// 班级名称
        ///</summary>
        private string class_name;
        public string Class_name
        {
            get { return class_name; }
            set { class_name = value; }
        }
 
        private student_index stuIndex;
        public student_index StuIndex
        {
            get { return stuIndex; }
            set { stuIndex = value; }
        }
    }
}
 
/// 索引器 /
namespace MySchool
{
    ///<summary>
    /// 学员索引器
    ///</summary>
    class student_index
    {
        // 建立一个student_my类数组
        public student_my[] myStu = new student_my[3];
        // 建立一个无参的构造函数,在这里实例化对象
        public student_index()
        {
            myStu[0] = new student_my(" 张三" ,29);
            myStu[1] = new student_my(" 李四" ,23);
            myStu[2] = new student_my(" 王五" ,18);
        }
        // 基本索引器根据数组下标查找学员
        public student_my this[int index]
        {
            get { return myStu[index]; }
        }
        重载的索引器根据姓名查找学员
        public student_my this[string name]
        {
            get
            {
                int i;
                bool found = false;
                for ( i = 0; i < myStu.Length; i++)
                {
                    if (myStu[i].Name == name)
                    {
                        found = true;
                        break;
                    }
                }
                if (found)
                {
                    return myStu[i];
                }
                else
                {
                    return null;
                }
            }
        }
    }
}
 
/// 索引器演示 /
Class_my cmy = new Class_my("s1125");
cmy.StuIndex[2].SayHi();
cmy.StuIndex[" 张三" ].SayHi(); 
 
 
( 如果有不对的或需要补充的地方 , 还请老师和同学们帮忙指出来 , 谢谢 !)
 
2010/3/26 整理
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值