WPF学习(3)--不同类通过接口实现同种方法

一、接口概述

1.接口的概念

在C#中,接口(interface)是一种引用类型,它定义了一组方法、属性、事件或索引器,但不提供实现。接口只定义成员的签名,而具体的实现由实现接口的类或结构体提供。接口使用关键字 interface 定义。

接口实例

cs 复制代码
public interface IShape
{
    double GetArea();
    double GetPerimeter();
    string GetInfo();
}

类实现接口实例

cs 复制代码
public class Circle : IShape
{
    public double Radius { get; set; }

    public Circle(double radius)
    {
        Radius = radius;
    }

    public double GetArea()
    {
        return Math.PI * Radius * Radius;
    }

    public double GetPerimeter()
    {
        return 2 * Math.PI * Radius;
    }

    public string GetInfo()
    {
        return $"Circle - Radius: {Radius}, Area: {GetArea():F2}, Perimeter: {GetPerimeter():F2}";
    }
}

2.使用接口的好处

  • 解耦和可替换性

    • 接口定义了行为的契约,而不关心具体的实现。这样,代码依赖于接口而不是具体实现,使得具体实现可以很容易地替换或修改而不影响使用接口的代码。
  • 提高代码的可测试性

    • 接口使得代码更容易进行单元测试。我们可以为接口创建模拟(Mock)对象,测试代码可以使用这些模拟对象来独立验证逻辑,而不需要依赖具体实现。

二、实例代码分析

1.Shapes.cs

cs 复制代码
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace WpfApp
{
    public interface IShape
    {
        double GetArea();
        double GetPerimeter();
        string GetInfo();
    }

    public class Circle : IShape
    {
        public double Radius { get; set; }

        public Circle(double radius)
        {
            Radius = radius;
        }

        public double GetArea()
        {
            return Math.PI * Radius * Radius;
        }

        public double GetPerimeter()
        {
            return 2 * Math.PI * Radius;
        }

        public string GetInfo()
        {
            return $"Circle - Radius: {Radius}, Area: {GetArea():F2}, Perimeter: {GetPerimeter():F2}";
        }
    }

    public class Rectangle : IShape
    {
        public double Width { get; set; }
        public double Height { get; set; }

        public Rectangle(double width, double height)
        {
            Width = width;
            Height = height;
        }

        public double GetArea()
        {
            return Width * Height;
        }

        public double GetPerimeter()
        {
            return 2 * (Width + Height);
        }

        public string GetInfo()
        {
            return $"Rectangle - Width: {Width}, Height: {Height}, Area: {GetArea():F2}, Perimeter: {GetPerimeter():F2}";
        }
    }
}

2.MainWindow.xmal.cs

cs 复制代码
using System;
using System.Collections.Generic; // 用于 List<T>
using System.ComponentModel; // 用于 INotifyPropertyChanged 接口
using System.Windows; // 用于 WPF 相关类

namespace WpfApp
{
    public partial class MainWindow : Window
    {
        // 存储形状的列表
        List<IShape> Shapes;
        
        // 存储形状信息的对象,用于数据绑定
        private ShapeInfo MyShapeInfo;

        // 构造函数,初始化组件和数据
        public MainWindow()
        {
            InitializeComponent();
            Shapes = new List<IShape>();
            MyShapeInfo = new ShapeInfo();
            MyShapeInfo.Info = ""; // 初始化 Info 属性
            DataContext = new { ShapeInfo = MyShapeInfo }; // 设置数据上下文
        }

        // 添加圆形按钮的点击事件处理程序
        private void Button_Click_AddCircle(object sender, RoutedEventArgs e)
        {
            double radius = DateTime.Now.Second; // 使用当前秒数作为圆的半径
            Circle circle = new Circle(radius); // 创建新的 Circle 对象
            Shapes.Add(circle); // 将 Circle 对象添加到列表中
        }

        // 添加矩形按钮的点击事件处理程序
        private void Button_Click_AddRectangle(object sender, RoutedEventArgs e)
        {
            double height = DateTime.Now.Second; // 使用当前秒数作为矩形的高度
            double width = height / 2; // 使用当前秒数的一半作为矩形的宽度
            Rectangle rectangle = new Rectangle(width, height); // 创建新的 Rectangle 对象
            Shapes.Add(rectangle); // 将 Rectangle 对象添加到列表中
        }

        // 显示形状信息按钮的点击事件处理程序
        private void Button_Click_ShowInfo(object sender, RoutedEventArgs e)
        {
            string info = "";
            // 遍历所有形状,获取其信息
            foreach (IShape shape in Shapes)
            {
                if (shape != null)
                {
                    info += shape.GetInfo(); // 获取形状信息
                    info += Environment.NewLine; // 添加换行符
                }
            }
            MyShapeInfo.Info = info; // 更新 ShapeInfo 对象的 Info 属性
            ShapesInfo.Text = MyShapeInfo.Info; // 更新 UI 中显示的信息
        }
    }

    // 用于存储和通知形状信息变化的类
    public class ShapeInfo : INotifyPropertyChanged
    {
        // 私有字段,存储信息字符串
        private string _info;

        // 公有属性,获取或设置信息字符串
        public string Info
        {
            get { return _info; }
            set
            {
                _info = value;
                OnPropertyChanged("Info"); // 通知属性值变化
            }
        }

        // 属性变化事件
        public event PropertyChangedEventHandler PropertyChanged;

        // 触发属性变化事件的方法
        protected virtual void OnPropertyChanged(string propertyName)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}

3.MainWindow.xmal

XML 复制代码
<Window x:Class="WpfApp.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Shape Info" Height="350" Width="525">
    <Grid>
        <StackPanel>
            <Button Content="Add Circle" Click="Button_Click_AddCircle" Margin="10"/>
            <Button Content="Add Rectangle" Click="Button_Click_AddRectangle" Margin="10"/>
            <Button Content="Show Shapes Info" Click="Button_Click_ShowInfo" Margin="10"/>
            <TextBlock Name="ShapesInfo" Margin="10" FontSize="16" TextWrapping="Wrap" Text="{Binding ShapeInfo.Info}"  />
        </StackPanel>
    </Grid>
</Window>

三、实验结果

相关推荐
long31642 分钟前
构建者设计模式 Builder
java·后端·学习·设计模式
咕白m6251 小时前
通过 C# 高效提取 PDF 文本的完整指南
后端·c#
杜子不疼.2 小时前
《Python学习之使用标准库:从入门到实战》
开发语言·python·学习
search72 小时前
前端学习 10 :SOC设计中的验证
学习
艾莉丝努力练剑3 小时前
【C语言16天强化训练】从基础入门到进阶:Day 1
c语言·开发语言·数据结构·学习
Magnetic_h4 小时前
【iOS】锁的原理
笔记·学习·macos·ios·objective-c·cocoa·xcode
hqwest4 小时前
C#WPF实战出真汁08--【消费开单】--餐桌面板展示
c#·wpf·ui设计·wpf界面设计
orangapple4 小时前
WPF 打印报告图片大小的自适应(含完整示例与详解)
c#·wpf
鸢栀w5 小时前
前端css学习笔记7:各种居中布局&空白问题
前端·css·笔记·学习·尚硅谷网课
Hero_11275 小时前
学习Stm32 的第一天
stm32·嵌入式硬件·学习