【全栈计划 —— 编程语言之C#】将类玩明白,把对象把持住

简介: 【全栈计划 —— 编程语言之C#】将类玩明白,把对象把持住


通过类能很好地体现面向对象语言中的三大特性——封装、继承、多态。


【一】、类的定义


类定义的语法如下:

类的访问修饰符 修饰符 类名
{
  类的成员
}

① 类的访问修饰符 —— 用于设定对类的访问限制

类的访问修饰符有2个

1)public : 可以在任何项目中访问改该类

2)internal/不写:只能在当前项目中访问该类

微信图片_20221020134532.png

② 修饰符 —— 对类本身特点的描述

包括 abstract、sealed 和 static

微信图片_20221020134555.png

③ 类名

类名和常规的取变量名类似,一般在取名的时候,最好能表现出该类的功能。在同一个命名空间下,类名必须是唯一的。

④ 类成员 —— 在类中能定义的元素

主要包括字段、属性、方法


【二】、类的成员


类中的成员包括字段、属性、方法。每个类成员在定义时需要指定访问修饰符、修饰符。


通用——访问修饰符


类中成员的访问修饰符有 4 个

1)public —— 成员可以被任何代码访问

2)private —— 成员仅能被同一个类中的代码访问


如果在类成员前没有使用任何修饰符,就默认为private

3)internal —— 成员仅能别同一个项目中的代码访问

4)protected—— 成员只能由类或者派生类中的代码访问


派生类是在继承中涉及


类的成员 —— 字段 and 属性


字段的定义与变量和常量的定义类似,只是在变量或常量前面可以加上访问修饰符、修饰符。


定义字段的语法形式如下:

访问修饰符 修饰符 数据类型 字段名;

字段的修饰符

修饰字段时通常用两个修饰符,即 readonly (只读)和static (静态的)

1)readonly —— 只能读取该字段的值而不能给字段赋值

微信图片_20221020134945.png

2)static —— 静态字段,可以直接通过类名访问

注意常量不能使用static修饰符 修饰


get访问器 和 set访问器

属性经常与字段连用,并提供了 get 访问器和 set 访问器,分别用于获取或设置字段的值。


知识普及一:

get访问器和set访问器的使用与方法的使用其实蛮类似的,可以在操作字段的时候,根据一些规则和条件来设置获取字段的值。


知识普及二:

可以选择性去除get访问器或者set访问器。


1)get{}

get访问器,用于设置获取属性的值,在最后需要使用return 返回一个与该属性数据类型想兼容的值。


若在属性定义中忽略了该访问器,则不能在其他类中获取私有类型的字段值,所以有时候也称为只写属性


2)set{}

set访问器用于设置字段的值,这里需要使用一个特殊的值value,把它用来为字段赋值。

在set访问器省略后,无法在其他类中给该字段赋值,所以也称为只读属性。


① 属性设置:

语法:

public    数据类型    属性名
{
    get
    {
        获取属性的语句块;
        return 值;
    }
    set
    {
        设置属性得到语句块;
    }
}

Tips: 由于属性都是针对某个字段赋值,因此属性的名称通常是将字段中每个单词的首字母大写。例如定义了一个名为 name 的字段,属性名则为 Name。


【随堂演练】定义一个图书信息类(Book),在类中定义图书编号(id)、图书名称(name)、图书价格(price)3 个字段,并分别为这 3 个字段设置属性,其中将图书名称设置为只读属性。


参考代码

using System;
namespace OOPDemo_1
{
    class Book
    {
        private int id;
        private string name;
        private double price;
        //设置图书编号属性
        public int Id
        {
            get
            {
                return id;
            }
            set
            {
                id = value;
            }
        }
        //设置图书名称属性
        //根据要求,将图书的书名设置为只读属性
        public string Name
        {
            get
            {
                return name;
            }
        }
        //设置图书价格属性
        public double Price
        {
            get
            {
                return price;
            }
            set
            {
                price = value;
            }
        }
    }
}

② 自动属性设置

定义语法:

public    数据类型    属性名{get;set;}

参考代码

public int Id{get; set;}
public string Name{get; set;}
public double Price{get; set;}

使用注意点一:

如果使用自动属性设置的方式来设置属性,大括号内不需要指定字段。

但是

如果想要把某个属性设置为只读属性,可以直接省略set访问器即可实现。

public int Id{get;}

如果此时还想要给某个属性值赋值,可以这种操作

//只读属性
public int Id{get;}=1;
//常规
public int Id{get; set;}=1;

微信图片_20221020135254.png

使用注意点二:

自动生成属性的方法不能省略get访问器,如果不允许其他类来访问该属性值,可以通过加private修饰符来实现。


public int Id{private get; set;}

类的成员 —— 方法


常规观念中的方法

主方法 Main()是执行程序的入口和出口

方法是将完成同一功能的内容放到一起,方便书写和调用的一种方式。也体现了面向对象语言中的封装性。

定义方法的语法:

访问修饰符    修饰符    返回值类型    方法名(参数列表)
{
    语句块;
}

1) 访问修饰符

所有修饰类成员的访问修饰符也可以用来修饰符方法。假如省略不写,则默认为private

2) 修饰符

微信图片_20221020135539.png

3)返回值类型


用于在调用方法后得到返回结果,返回值可以是任意的数据类型,如果指定了返回值类型,必须使用 return 关键字返回一个与之类型匹配的值。

如果没有指定返回值类型,必须使用 void 关键字表示没有返回值。

4)方法名


方法名的命名是以 Pascal 命名法为规范的。支持重名,因为有方法的重载

image.png5)参数列表

在方法中允许有 0 到多个参数,如果没有指定参数也要保留参数列表的小括号。

参数的定义形式是数据类型 参数名,如果使用多个参数,多个参数之间需要用逗号隔开。

微信图片_20221020135637.png

构造方法

① 构造方法的名字是与类的名称相同的

创建类的对象是使用类名 对象名 = new 类名()的方式来实现的。

实际上,此处的类名()的形式调用的是类的构造方法


对于创建对象这块,假如在new 的类中没有自定义构造方法,此时会使用系统默认生成的一个不带参数的构造方法。


② 构造方法的定义语法

访问修饰符  类名 (参数列表)
{
    语句块;
}

这里构造方法的访问修饰符通常是public类型的,这样在其他类中都可以创建该类的对象

如果将访问修饰符设置成private类型的,则无法创建该类的对象。


构造方法中的参数与其他方法一样,都是 0 到多个参数。


Tips:正是因为其可带参数,因此可以将一些类成员初始化的操作放到构造方法中去完成,这种既可以创建对象,也可以初始化对象

微信图片_20221020135723.png折构方法

折构方法了解就好,析构方法则是在垃圾回收、释放资源时使用的。

暂时和咱们有点遥远。先积累。

折构方法定义语法

~类名()
{
    语句块;
}

微信图片_20221020135911.png

在调用重载的方法时系统是根据所传 递参数的不同判断调用的是哪个方法。


方法的重载还是比较容易理解的,想着重拓展一下关于方法参数的知识


① 实参和形参

方法中的参数分为实际参数和形式参数。

实际参数被称为实参,是在调用方法时传递的参数;

形式参数被称为形参,是在方法定义中所写的参数。


② 引用参数和输出参数

方法中的参数除了定义数据类型外,还可以定义引用参数和输出参数。

引用参数使用 ref 关键字定义;

输出参数使用 out 关键字定义。


需要注意的两个点:


1)在调用带有引用参数的方法时,实际参数必须是一个变量,不能是变量或者表达式等等,并且在传值时必须加上 ref 关键字。


当是表达式的时候会报错:

微信图片_20221020135953.jpg

当是常量的时候,也会出现报错微信图片_20221020140016.jpg

2) 使用输出参数时,必须在方法调用完成前为输出参数赋值

引用参数与我们平时使用的参数有些类似,但输出参数不同,输出参数相当于返回值,即在方法调用完成后可以将返回的结果存放到输出参数中。


输出参数多用于一个方法需要返回多个值的情况。

在使用输出参数时,必须在传递参数时使用 out 关键字,但不必给输出参数赋值;

在方法调用完成前为输出参数赋值。

image.jpeg演示代码

using System;
using System.Collections.Generic;
using System.Text;
/*
 * 【实例 1】创建名为 RefClass 的类,
 * 在类中定义一个判断所输入整数是否为 5 的倍数的方法,
 * 并将方法中传入的整数参数定义为 ref 类型的。
 */
namespace OOPDemo_1
{
    class RefClass
    {
        public bool Judge(ref int num)
        {
            if ((num % 5) == 0) return true;
            else return false;
        }
    }
}
/*******************************************************/
using System;
using System.Collections.Generic;
using System.Text;
/*
 * 【实例 2】创建一个 OutClass 类,在类中定义与【实例 1】类似的方法,
 * 只是在方法的参 数中增加一个输出参数,用于返回判断的结果。
 */
namespace OOPDemo_1
{
    class OutClass
    {
        public void Judge(int num,out bool result)
        {
            if (num % 5 == 0) result = true;
            else result = false;
        }
    }
}
/*******************************************************/
using System;
namespace OOPDemo_1
{
    class Program
    {
        static void Main(string[] args)
        {
         RefClass refClass = new RefClass();
            int a = 20;
            //int b = 23;
            //const int N = 5;
            //在调用带有引用参数的方法时,实际参数必须是一个变量,并且在传值时必须加上 ref 关键字。
            bool res = refClass.Judge(ref a);
            Console.WriteLine("验证结果是:" + res);
            //调用含有带输出参数的方法时,必须在传递参数时使用 out 关键字,但不必给输出参数赋值
            OutClass outClass = new OutClass();
            bool rs;
            outClass.Judge(a, out rs);
            Console.WriteLine(rs);
            }
        }
 }

调用类成员


调用类的成员需要使用这个类的对象,对于创建类的对象。

创建类对象的语法形式如下:

类名 对象名 = new 类名();

上面的语法形式是一种简单形式,通过对象名结合.运算符即可调用类中的成员。

调用的语法形式如下:

对象名 . 类的成员

对于类的对象,我自己的理解是他是一个代理。

比如华为手机是一个类,Mate 40是创建的一个实例化对象,那么这个Mate 40就可以执行华为手机中的所有功能。

环节一 —— 创建对象以及调用方法

【随堂练习】在Book1类中添加一个方法,用于输出该类中的所有属性。

using System;
using System.Collections.Generic;
using System.Text;
namespace OOPDemo_1
{
    class Book1
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public double Price { get; set; }
        public void PrintMsg()
        {
            Console.WriteLine("图书编号:" + Id);
            Console.WriteLine("图书名称:" + Name);
            Console.WriteLine("图书价格:" + Price);
        }
    }
}

在项目的 Program.cs 文件里的 Main 方法中,加入调用 PrintMsg() 方法的代码。

微信图片_20221020142001.jpg

  class Program
  {
      static void Main(string[] args)
      {
          Book1 book1 = new Book1();
          book1.PrintMsg();
      }
  }

执行结果

微信图片_20221020142238.png

环节二 —— 对属性赋值并输出

通过对象调用相应的属性,进行赋值:

class Program
{
    static void Main(string[] args)
    {
        Book1 book1 = new Book1();
        //为属性赋值
        book1.Id = 520;
        book1.Name = "围城";
        book1.Price = 131.4;
        book1.PrintMsg();
    }
}

【课堂练习】在 Book1 类中添加一个向属性赋值的方法,并在 Main 方法中调用。

class Book1
{
    public int Id { get; set; }
    public string Name { get; set; }
    public double Price { get; set; }
    public void SetBook(int id, string name, double price)
    {
        Id = id;
        Name = name;
        Price = price;
    }
    public void PrintMsg()
    {
        Console.WriteLine("图书编号:" + Id);
        Console.WriteLine("图书名称:" + Name);
        Console.WriteLine("图书价格:" + Price);
    }
}
/**********************主函数代码***********************************/
class Program
{
    static void Main(string[] args)
    {
        Book1 book1 = new Book1();
        book1.SetBook(520, "计围城", 131.4);
        book1.PrintMsg();
    }
}

如果要取得属性的值,直接使用类的对象.属性名即可;

如果给属性赋值的代码如下:

类的对象 . 属性名 = 值;

使用类的对象调用方法的代码:

类的对象 . 方法名(参数);

Tips:如果将类中的成员使用修饰符 static 声明,则在访问类成员时直接使用类名.类成员的方式即可。


【三】、知识积累——常用常见类


① Console 类 —— Console 类主要用于控制台应用程序的输入和输岀操作。

我现阶段认为重要的,常用的方法有这四个:

微信图片_20221020142506.png

补充格式化输出

此外,在向控制台中输出内容时也可以对输出的内容进行格式化,格式化时使用的是占位符的方法,语法形式如下:

Console.Write(格式化字符串, 输出项1, 输出项2);

其中,在格式化字符串中使用{索引号}的形式,索引号从 0 开始。输出项 1 填充 {0} 位置的内容,依此类推。

微信图片_20221020142532.png

现阶段,我认为比较值得掌握的属性有这三个:

微信图片_20221020142727.png

至于其他更加详细的解说和总结,大家可以参考【微软C#官方文档——Console类】

② Math 类 —— Math 类主要用于一些与数学相关的计算,并提供了很多静态方法方便访问

Math类的常用方法还蛮多的,注意Max 和 Min 这两个超级常用

微信图片_20221020142748.png

Tips:用的时候,一定要注意返回值类型,具体在使用之前,可以通过官方文档查阅

【Math 类官方文档】

③ Random 类 —— Random 类是一个产生伪随机数字的类

它的构造函数有两种:
New Random();
New Random(Int32)。

前者是根据触发那刻的系统时间做为种子,来产生一个随机数字;

后者可以自己设定触发的种子,一般都是用 UnCheck((Int)DateTime.Now.Ticks) 做为参数种子。

Random中的常用方法:微信图片_20221020142836.png

想深入学习的,可以阅读一个官方文档了【Random 类 官方文档】

测试代码

class Program
{
    static void Main(string[] args)
    {
        Random rd = new Random();
        Console.WriteLine("产生一个10以内的数:{0}", rd.Next(0, 10));
        Console.WriteLine("产生一个0到1之间的浮点数:{0}", rd.NextDouble());
        byte[] b = new byte[5];
        rd.NextBytes(b);
        Console.WriteLine("产生的byte类型的值为:");
        foreach(byte i in b)
        {
            Console.Write(i + " ");
        }
        Console.WriteLine();
    }
}

④ DateTime 类 —— ateTime 类用于表示时间


这个我觉得蛮常用的,所表示的范围是从 0001 年 1 月 1 日 0 点到 9999 年 12 月 31 日 24 点。


一个重要的静态方法:

在 DateTime 类中提供了静态属性 Now,用于获取当前的日期和时间:

如下所示:


DateTime.Now

image.png

DateTime 结构 官方文档】


⑤ 嵌套类


核心知识


如果在其他类中调用嵌套类的成员,需要使用外部类.嵌套类的方式创建嵌套类的对象,从而通过嵌套类的对象调用其成员。

如果调用的是嵌套类中的静态成员,直接通过外部类 . 嵌套类 . 静态成员的方式调用即可。


嵌套类定义:

在类中除了能编写字段、属性、方法,还能直接定义类。将一个类定义在另一个类的内部,即可将在类内部定义的类称为嵌套类。

在 C# 中嵌套类相当于类中的成员,能使用类成员的访问修饰符和修饰符。但是,在访问嵌套类中的成员时必须加上外层类的名称。


测试代码

class OuterClass
{
  //在OuterClaSS 类中 嵌套 InnerClass
    public class InnerClass
    {
        public string CardId { get; set; }
        public string Password { get; set; }
        public void PrintMsg()
        {
            Console.WriteLine("卡号为:" + CardId);
            Console.WriteLine("密码为:" + Password);
        }
    }
}
/***************************主函数代码****************************************/
class Program
{
    static void Main(string[] args)
    {
        OuterClass.InnerClass outInner = new OuterClass.InnerClass();
        outInner.CardId = "1314520";
        outInner.Password = "123456";
        outInner.PrintMsg();
        Console.ReadKey();
    }
}

面向对象三大特征之一 —— 封装性


C# 封装根据具体的需要,设置使用者的访问权限,并通过 访问修饰符 来实现。

一个 访问修饰符 定义了一个类成员的范围和可见性。

public

所有对象都可以访问
private

对象本身在对象内部可以访问

protected 只有该类对象及其子类对象可以访问
internal 同一个程序集的对象可以访问


//

知道要用这四个访问修饰符来落实封装性就可以了,具体的深入展开要结合项目。


总结


对本篇文章而言,重要的是拿捏住以下四板知识内容:


① 区分清楚用于类的访问修饰符、修饰符以及用于类的成员的访问修饰符、修饰符

② 记清楚类中成员,以及如何构建对象,如何调用属性、方法,如何修改属性值

③ 积累常见类

④ 知道面向对象有三大特性,封装是如何实现的。


相关文章
|
1月前
|
开发框架 .NET C#
C#|.net core 基础 - 删除字符串最后一个字符的七大类N种实现方式
【10月更文挑战第9天】在 C#/.NET Core 中,有多种方法可以删除字符串的最后一个字符,包括使用 `Substring` 方法、`Remove` 方法、`ToCharArray` 与 `Array.Copy`、`StringBuilder`、正则表达式、循环遍历字符数组以及使用 LINQ 的 `SkipLast` 方法。
|
2月前
|
存储 C# 索引
C# 一分钟浅谈:数组与集合类的基本操作
【9月更文挑战第1天】本文详细介绍了C#中数组和集合类的基本操作,包括创建、访问、遍历及常见问题的解决方法。数组适用于固定长度的数据存储,而集合类如`List<T>`则提供了动态扩展的能力。文章通过示例代码展示了如何处理索引越界、数组长度不可变及集合容量不足等问题,并提供了解决方案。掌握这些基础知识可使程序更加高效和清晰。
81 2
|
1月前
|
编译器 C#
C#多态概述:通过继承实现的不同对象调用相同的方法,表现出不同的行为
C#多态概述:通过继承实现的不同对象调用相同的方法,表现出不同的行为
116 65
|
11天前
|
JSON 程序员 C#
使用 C# 比较两个对象是否相等的7个方法总结
比较对象是编程中的一项基本技能,在实际业务中经常碰到,比如在ERP系统中,企业的信息非常重要,每一次更新,都需要比较记录更新前后企业的信息,直接比较通常只能告诉我们它们是否指向同一个内存地址,那我们应该怎么办呢?分享 7 个方法给你!
|
1月前
|
Java 程序员 C#
【类的应用】C#应用之派生类构造方法给基类构造方法传参赋值
【类的应用】C#应用之派生类构造方法给基类构造方法传参赋值
13 0
|
2月前
|
C# 数据安全/隐私保护
C# 一分钟浅谈:类与对象的概念理解
【9月更文挑战第2天】本文从零开始详细介绍了C#中的类与对象概念。类作为一种自定义数据类型,定义了对象的属性和方法;对象则是类的实例,拥有独立的状态。通过具体代码示例,如定义 `Person` 类及其实例化过程,帮助读者更好地理解和应用这两个核心概念。此外,还总结了常见的问题及解决方法,为编写高质量的面向对象程序奠定基础。
27 2
|
3月前
|
C#
C#中的类和继承
C#中的类和继承
43 6
|
3月前
|
Java C# 索引
C# 面向对象编程(一)——类
C# 面向对象编程(一)——类
35 0
|
3月前
|
开发框架 .NET 编译器
C# 中的记录(record)类型和类(class)类型对比总结
C# 中的记录(record)类型和类(class)类型对比总结
|
5月前
|
开发框架 .NET 编译器
程序与技术分享:C#基础知识梳理系列三:C#类成员:常量、字段、属性
程序与技术分享:C#基础知识梳理系列三:C#类成员:常量、字段、属性
37 2