C#基础入门第十三天(多态接口)
第十二天复习
namespace 复习 { class Program { static void Main(string[] args) { /* Lisi<T> Dictionary<K,T> 拆装箱 装箱:值类型转为引用类型 拆箱:引用类型转为值类型 应该尽量避免在代码中发生 文件流 FileStream StreamReader和StreamWrite 多态:虚方法、抽象类、接口 虚方法 抽象类 */ //List<int> list = new List<int>(); //Dictionary<int, string> dic = new Dictionary<int, string>(); //dic.Add(1, "张三"); //dic[2] = "李四"; //foreach (KeyValuePair<int ,string> kv in dic) //{ // Console.WriteLine("{0}----{1}", kv.Key, kv.Value); //} //Console.ReadKey(); //File FileStream StreamReader StreamWrite //using (FileStream fsRead = new FileStream("1.txt", FileMode.OpenOrCreate, FileAccess.Read)) //{ // byte[] buffer = new byte[1024 * 1024 * 5]; // int r = fsRead.Read(buffer, 0, buffer.Length); // string s = Encoding.UTF8.GetString(buffer, 0, r); // Console.WriteLine(s); //} //Console.ReadKey(); //using (FileStream fsWrite = new FileStream(@"C:\Users\Administrator\Desktop\new.txt", FileMode.OpenOrCreate, FileAccess.Write)) //{ // string s = "今天的内容有点多啊"; // byte[] buffer = Encoding.UTF8.GetBytes(s); // fsWrite.Write(buffer, 0, buffer.Length); //} //Console.WriteLine("OK"); //Console.ReadKey(); //虚方法和抽象类 //老师可以起立,学生也可以起立,校长也可以起立 //Person p = new Student(); //p.StanUp(); //Console.ReadKey(); } } public abstract class Person { public abstract void StanUp(); } public class Student : Person { public override void StanUp() { Console.WriteLine("学生起立,说老师好"); } } public class Teachar : Person { public override void StanUp() { Console.WriteLine("老师起立说校长好"); } } public class HeadMaster : Person { public override void StanUp() { Console.WriteLine("请坐"); } }
}
第十三天新内容
一、C#中的访问修饰符
public:公开的,公共的
private: 私有的,只能在当前类的内部访问
protected: 受保护的,只能在当前类的内部以及该类的子类中访问
internal:只能在当前程序集中访问,在同一个项目中和public的权限是一样的。
protected internal:protected和internal的权限相加
1.能够修饰类的访问修饰符只有:public和internal
2.可访问性不一致
子类的权限不能高于父类的权限,不然会暴露父类的成员
二、设计模式(设计这个项目的一种方式。)
简单工厂设计模式
namespace _03简单工厂设计模式 { class Program { static void Main(string[] args) { Console.WriteLine("请输入你需要的笔记本品牌"); string note = Console.ReadLine(); NoteBook nb = GetNoteBook(note); nb.SayHello(); Console.ReadKey(); } /// <summary> /// 简单工厂的核心,根据用户输入的对象来赋值给父类 /// </summary> /// <param name="note"></param> /// <returns></returns> public static NoteBook GetNoteBook(string note) { NoteBook nb = null; switch (note) { case "Lenove" : nb = new Lenovo(); break; case "Acre" : nb = new Acre(); break; case "Dell" : nb = new Dell(); break; case "Hp" : nb = new Hp(); break; } return nb; } } public abstract class NoteBook { public abstract void SayHello(); } public class Lenovo : NoteBook { public override void SayHello() { Console.WriteLine("我是联想笔记本,你连想都别想"); } } public class Acre : NoteBook { public override void SayHello() { Console.WriteLine("我是宏碁笔记本"); } } public class Dell : NoteBook { public override void SayHello() { Console.WriteLine("我是戴尔笔记本"); } } public class Hp : NoteBook { public override void SayHello() { Console.WriteLine("我是惠普笔记本"); } } }
三、值类型和引用类型的传递
值类型在复制的时候,传递时是这个值得本身
引用类型在复制的时候,传递的是对这个对象的引用
四、序列化和反序列化
序列化:将对象转换为二进制
反序列化:将二进制转换为对象
作用:传输数据
序列化:
1、将这个类标记为可以被序列化的,在类上面加关键字:[Serializable]
语法
namespace _04序列化和反序列化 { class Program { static void Main(string[] args) { ////序列化 //Person p = new Person(); //p.Name = "张三"; //p.Age = 18; //p.Gender = '男'; //using (FileStream fsWrite = new FileStream(@"C:\Users\Administrator\Desktop\111.txt", FileMode.OpenOrCreate, FileAccess.Write)) //{ // //开始序列化对象 // BinaryFormatter bf = new BinaryFormatter(); // bf.Serialize(fsWrite, p); //} //Console.WriteLine("写入成功"); //Console.ReadKey(); //接收对方发送过来的二进制 反序列化成对象 Person p; using (FileStream fsRead = new FileStream(@"C:\Users\Administrator\Desktop\111.txt", FileMode.OpenOrCreate, FileAccess.Read)) { BinaryFormatter bf = new BinaryFormatter(); p = (Person)bf.Deserialize(fsRead); } Console.WriteLine(p.Name); Console.WriteLine(p.Age); Console.WriteLine(p.Gender); Console.ReadKey(); } } [Serializable] public class Person { private string _name; public string Name { get { return _name; } set { _name = value; } } private int _age; public int Age { get { return _age; } set { _age = value; } } private char _gender; public char Gender { get { return _gender; } set { _gender = value; } } } }
五、部分类
在同一个命名空间下写同名的类,关键字:partial
多用于多人开发时需要写一个类
语法
public partial class Person
六、密封类
不能够被继承,但是密封类能够继承其他类
语法
public sealed class Person
七、重写ToString方法
所有的东西都能ToString,应为ToString是Object的方法,所有的对象都是Object的子类
语法
namespace _05重写ToString方法 { class Program { static void Main(string[] args) { Person p = new Person(); Console.WriteLine(p.ToString()); Console.ReadKey(); } } public class Person { public override string ToString() { return "Hello word"; } } }
八、接口(接口就是一个规范,能力)
语法
[public] interface I...able
{
//接口中的成员不允许添加访问修饰符,默认就是public
//接口中,不允许具有方法体的函数,不能包含字段
//接口中,可以写自动属性(没写,但是编译时候会自动生成)
public int Age
{
get;
set;
}
成员...
}
接口的成员有:方法、自动属性、索引器 但是:自动属性本质也是两个函数,索引器也是函数。所以:接口的成员就有:方法
接口的特点:
接口是一种规范,只要一个类继承一个接口,这个类就必须实现这个接口中所有的成员
public class Person : IFyable { //实现这个接口中所有的成员 public void Fly() { Console.WriteLine("飞"); } } public interface IFyable { void Fly(); }
为了多态,接口不能被实例化。也就是说,接口不能new(不能创建对象)
static void Main(string[] args) { //接口是不能被实例化的,因为接口中的成员没有方法体 // IFyable fly = new IFyable(); //如果要想实现多态,则需要指向一个对象 IFyable fly = new Person(); fly.Fly(); Console.ReadKey(); }
接口中的成员不能加“访问修饰符”,接口中的成员访问修饰符默认为public,不能修改。接口中的成员不能有任何实现(“光说不练”,只是定义一组未实现的成员。类似于抽象类中的抽象函数)
接口中只能有方法、自动属性、索引器、事件,不能有“字段”和构造函数
接口与接口之间可以继承,并且可以多继承
public interface M1 { void Test1(); } public interface M2 { void Test2(); } public interface M3 { void Test3(); } public interface M4:M1,M2,M3 { } public class Cat : M4 { public void Test1() { throw new NotImplementedException(); } public void Test2() { throw new NotImplementedException(); } public void Test3() { throw new NotImplementedException(); } }
接口并不能去继承一个类,而类可以继承接口(接口只能继承于接口,而类即可继承接口,也可继承类)
实现接口的子类,必须实现该接口的全部成员
一个类可以同时继承一个类并实现多个接口,如果一个子类同时继承父类A。并实现接口接口IA,那么语法上A必须写在IA的前面
语法:
public class B:A,IA
{
类成员
}
由于全网这套视频在接口这里有问题,留待复习时候来搞
namespace _06接口 { class Program { static void Main(string[] args) { //接口是不能被实例化的,因为接口中的成员没有方法体 // IFyable fly = new IFyable(); //如果要想实现多态,则需要指向一个对象 IFyable fly = new Person(); fly.Fly(); Console.ReadKey(); } } public class Person : IFyable { //实现这个接口中所有的成员 public void Fly() { Console.WriteLine("飞"); } } public interface IFyable { void Fly(); } public interface M1 { void Test1(); } public interface M2 { void Test2(); } public interface M3 { void Test3(); } public interface M4:M1,M2,M3 { } public class Cat : M4 { public void Test1() { throw new NotImplementedException(); } public void Test2() { throw new NotImplementedException(); } public void Test3() { throw new NotImplementedException(); } } }
九、显示实现接口(为了解决方法的重名问题)
语法及用法
namespace _07显示实现接口 { class Program { static void Main(string[] args) { IFlyable fly = new bird(); fly.Fly(); bird bi = new bird(); bi.Fly(); Console.ReadKey(); } } public class bird:IFlyable { public void Fly() { Console.WriteLine("鸟会飞"); } /// <summary> /// 显示实现接口 /// </summary> void IFlyable.Fly() { Console.WriteLine("我是接口的飞"); } } public interface IFlyable { void Fly(); } }
总结:
1、什么时候用虚方法来实现多态
在提供出来的类中,能抽象出来一个父类,父类必须写上子类共有的方法,知道这个方法怎么写,并且还需要创建父类的对象,这时候就使用虚方法
2、什么时候用抽象类来实现多态
在提供出来的类中,能抽象出来一个父类,父类必须写上子类共有的方法,并且不知道这个方法怎么写,这时候就使用抽象类
3、什么时候用接口来实现多态
几个类中,找不出父类,但是他们都有一个共同的行为,就时候就使用接口
接口练习
namespace _08接口练习 { class Program { static void Main(string[] args) { //真的鸭子会游泳,木头鸭子不会游泳,橡皮鸭子会游泳 ISwimming swim = new RealDuck(); swim.Swim(); Console.ReadKey(); } } public class RealDuck : ISwimming { public void Swim() { Console.WriteLine("真的鸭子会游泳"); } } public class MuDuck { } public class XPDuck : ISwimming { public void Swim() { Console.WriteLine("橡皮鸭子漂着游泳"); } } public interface ISwimming { void Swim(); } }
综合实战:超市收银系统
分析系统需求
超市提供的商品:笔记本电脑、手机、酱油、香蕉
商品在超市里面应该有:价格、数量、编号
这样就能抽象出来一个父类(ProductFather),包含价格(Price)、数量(Count)、编号(ID)
如果东西不够卖了,需要到仓库拿货物
仓库需要的功能:存储货物、提货、进货
超市卖东西时候需要一个收银的功能
抽象出一个商品的父类
class ProductFather { public decimal Price { get; set; } public double Count { get; set; } public string ID { get; set; } public ProductFather(string id, decimal price, double count) { this.ID = id; this.Price = price; this.Count = count; } }
分别创建商品类继承于父类
class ShouJi:ProductFather { public ShouJi(string id, decimal price, double count) : base(id, price, count) { } }
创建仓库类
class CangKu
{
//1.存储货物
//1.1 list相当于仓库,List<ProductFather>添加数据的集合,相当于将货架放到仓库,从而分门别类
List<List<ProductFather>> list = new List<List<ProductFather>>();
/// <summary> /// 想用户展示货物 /// </summary> public void ShowPros() { foreach (var item in list) { Console.WriteLine("仓库有:" + item[0].Name + "," + "\t" + "有" + item.Count + "个," + "\t" + "每个" + item[0].Price + "元。"); } } /// <summary> /// 创建仓库对象时,向仓库中添加货架 /// </summary> //list[0] 存电脑 list[1]存手机 list[2]存酱油 list[3]存香蕉,这时候如果多,就能通过循环来完成 public CangKu() { list.Add(new List<ProductFather>()); list.Add(new List<ProductFather>()); list.Add(new List<ProductFather>()); list.Add(new List<ProductFather>()); } /// <summary> /// 进货 /// </summary> /// <param name="strType">货物的类型</param> /// <param name="count">货物的数量</param> public void GetPros(string strType,int count) { for (int i = 0; i < count; i++) { switch (strType) { case "NoteBook": list[0].Add(new NoteBook(Guid.NewGuid().ToString(), 5000, "笔记本电脑")); break; case "ShouJi":list[1].Add(new ShouJi(Guid.NewGuid().ToString(), 3000, "手机")); break; case "JiangYou":list[2].Add(new JiangYou(Guid.NewGuid().ToString(), 10, "酱油")); break; case "Banana":list[3].Add(new Banana(Guid.NewGuid().ToString(), 20, "香蕉")); break; } } } /// <summary> /// 取货 /// </summary> /// <param name="strType">货物的类型</param> /// <param name="count">货物的数量</param> //货物取出后,需要放哪?而且有可能会拿很多个所以返回ProductFather[] public ProductFather[] QuPros(string strType, int count) { ProductFather[] pros = new ProductFather[count]; for (int i = 0; i < count; i++) { switch (strType) { case "NoteBook": if (list[0].Count == 0) { Console.WriteLine("没有电脑了!"); } else { pros[i] = list[0][0]; list[0].RemoveAt(0); } break; case "ShouJi": if (list[1].Count == 0) { Console.WriteLine("没有手机了!"); } else { pros[i] = list[1][0]; list[1].RemoveAt(0); } break; case "JiangYou": if (list[2].Count == 0) { Console.WriteLine("没有酱油了!"); } else { pros[i] = list[2][0]; list[2].RemoveAt(0); } break; case "Banana": if (list[3].Count == 0) { Console.WriteLine("没有酱油了!"); } else { pros[i] = list[3][0]; list[3].RemoveAt(0); } break; } } return pros; } }
- 八、C#入门基础08(封装,继承,多态)
- 九、C#入门基础09(接口,抽象类和抽象方法)
- java 从零开始,学习笔记之基础入门<抽象类_接口_多态>(十三)
- C#基础总结之八面向对象知识点总结-继承与多态-接口
- C#接口入门基础知识复习
- C#基础-----接口实现多态
- C#学习第十三天 实现多态:接口;MD5加密
- 黑马程序员:C#基础篇(四)抽象类、接口、继承与多态
- C#基础--类/接口/成员修饰符,多态、重载、重写,静态和非静态
- Java入门基础(三)面像对象——多态、接口
- c# 接口interface基础入门小例子
- C#基础知识(十一)——泛型集合、文件管理、多态、接口
- 基于C#的接口基础教程
- 2020.3.23----java接口基础以及多态
- JAVA基础知识:多态;接口
- java基础-java与c#接口不同点
- ASP.NET入门随想之多态、接口与委托
- C#轻松入门(三)面向对象的编程基础
- [Backgammon] Java基础学习入门(封装,多态,抽象类,final修饰符)
- 基于C#的接口基础教程之四_C#教程