什么是接口和抽象类?

发布时间:2022-07-03 发布网站:脚本宝典
脚本宝典收集整理的这篇文章主要介绍了什么是接口和抽象类?脚本宝典觉得挺不错的,现在分享给大家,也给大家做个参考。

谨记:设计严谨的软件重要的标准就是需要经的起测试,一个程序好不好被测试,测试发现问题能不能被良好的修复,程序状况能否被监控,这都有赖于对抽象类和接口的正确使用。

接口和抽象类,是高阶面向对象设计的起点。想要学习设计模式,必须有着对抽象类和接口的良好认知,和SOLID的认知,并在日常工作中正确的使用他们。

 

先简述一下SOLID的特指的五种原则,优秀的设计模式,都是参考于这五种原则的实现;

SOLID:

SRP: Single ResponsibilITy PRinciple 单一职责原则

OCP: OPEn Closed Principle 开闭原则

LSP: Liskov Substitution Principle 里氏替换原则

ISP:  Interface Segregation Principle 接口隔离原则

DIP: Dependency Inversion Principle 依赖反转原则

 

什么是接口和抽象类:

  • 接口和抽象类都是 “软件工程产物”
  • 具体类——抽象类——接口:越来越抽象,内部实现的东西越来越少
  • 抽象类是未完全实现逻辑的类(可以有字段和非public成员,他们代表了 “具体逻辑”)
  • 抽象类为复用而生:专门作为基类来使用,也具有解耦的功能。
  • 抽象类封装的是确定的开放的是不确定的,推迟到合适的子类中去实现。
  • 接口是完全未实现逻辑的 “类”,(“纯虚类”;只有函数成员;成员默认为public且不能为private) 但在新的C#版本中,接口也能拥有属性,索引,事件,和方法的默认实现。
  • 接口为解耦而生:“高内聚,底耦合”,方便单元测试。
  • 接口是一个 “协约”,它规定你必须有什么。
  • 它们都不能实例化,只能用来声明变量,引用具体类的实例。

 

为做基类而生的 “抽象类”与 “开放/关闭原则”: (所有的规则都是为了更好的协作)

我们应该封装那些不变的,稳定的,确定的而把那些不确定的,有可能改变的成员声明为抽象成员,并且留给子类去实现。

错误的功能封装实现:违反了开闭原则,每当新增功能就会新增代码

什么是接口和抽象类?

什么是接口和抽象类?

    class Program
    {
        static void Main(string[] args)
        {
            Vehicle vehicle = new Car();
            vehicle.Run("car");
        }
    }

    class Vehicle
    {
        public void Stop()
        {
            Console.WriteLine("stopped!");
        }

        public void Fill()
        {
            Console.WriteLine("Pay and fill...");
        }

        public void Run(string type)
        {
            //这时候又来一辆车 我们又得加代码了 破坏了 开闭原则
            switch (type)
            {
                case "car":
                    Console.WriteLine("car is running...");
                    break;
                case "truck":
                    Console.WriteLine("truck is running...");
                    break;
                default:
                    break;
            }
        }

    }

    class Car : Vehicle
    {
        public void Run()
        {
            Console.WriteLine("car is running...");
        }
    }

    class Truck : Vehicle
    {
        public void Run()
        {
            Console.WriteLine("truck is running...");
        }
    }
View Code

利用多态的机制优化上述代码:

什么是接口和抽象类?

什么是接口和抽象类?

class Program
{
    static void Main(string[] args)
    {
        Vehicle vehicle = new Car();
        vehicle.Run();
    }
}

class Vehicle
{
    public void Stop()
    {
        Console.WriteLine("stopped!");
    }

    public void Fill()
    {
        Console.WriteLine("Pay and fill...");
    }

    public virtual void Run()
    {
        Console.WriteLine("vehicle is running...");
    }

}

class Car : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("car is running...");
    }
}

class Truck : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("truck is running...");
    }
}
多态优化

我们可以发现vehicle的Run方法,我们基本上很少能用到,那我们去掉它的方法实现,一个虚方法却没有函数实现,这不就是纯虚方法了吗? 在C#中,纯虚方法的替代类型是abstract。

在现在这个方法中,它封装了确定的方法,开放了不确定的方法,符合了抽象类的设计,也遵循了开闭/原则。

什么是接口和抽象类?

什么是接口和抽象类?

class Program
{
    static void Main(string[] args)
    {
        Vehicle vehicle = new Car();
        vehicle.Run();
    }
}

//封装出了确定的方法 开放了不确定的方法
abstract class Vehicle
{
    public void Stop()
    {
        Console.WriteLine("stopped!");
    }

    public void Fill()
    {
        Console.WriteLine("Pay and fill...");
    }

    public abstract void Run();
}

class Car : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("car is running...");
    }
}

class Truck : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("truck is running...");
    }
}
抽象类优化

这个时候我们如果想要新增一个类型的汽车,只需要继承并实现它的抽象方法即可,这更符合开闭/原则。

现在我们让VehicleBase做为纯抽象类,这在C#中是一种常见的模式,我们可以分“代”的来完成开放的不确定方法,让方法慢慢变得清晰和确定。

什么是接口和抽象类?

什么是接口和抽象类?

class Program
{
    static void Main(string[] args)
    {
        Vehicle vehicle = new Car();
        vehicle.Run();
    }
}

abstract class VehicleBase
{
    public abstract void Stop();
    public abstract void Fill();
    public abstract void Run();
}

abstract class Vehicle : VehicleBase
{
    public override void Fill()
    {
        Console.WriteLine("pay and fill...");
    }

    public override void Stop()
    {
        Console.WriteLine("stopped!");
    }
}

class Car : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("car is running...");
    }
}

class Truck : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("truck is running...");
    }
}
纯抽象类的优化

让我们在思考下去,纯抽象类,不就是接口的默认实现模式吗,我们将纯抽象类改成接口。

什么是接口和抽象类?

什么是接口和抽象类?

class Program
{
    static void Main(string[] args)
    {
        Vehicle vehicle = new Car();
        vehicle.Run();
    }
}

interface IVehicle
{
    void Stop();
    void Fill();
    void Run();
}

abstract class Vehicle : IVehicle
{
    public void Fill()
    {
        Console.WriteLine("pay and fill...");
    }

    public void Stop()
    {
        Console.WriteLine("stopped!");
    }
    abstract public void Run();
}

class Car : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("car is running...");
    }
}

class Truck : Vehicle
{
    public override void Run()
    {
        Console.WriteLine("truck is running...");
    }
}
接口的优化

这是不是就熟悉多了,这是一种良好的设计方法了。

 

脚本宝典总结

以上是脚本宝典为你收集整理的什么是接口和抽象类?全部内容,希望文章能够帮你解决什么是接口和抽象类?所遇到的问题。

如果觉得脚本宝典网站内容还不错,欢迎将脚本宝典推荐好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:384754419,请注明来意。