浅学C#(13)——运算符重载、隐式类型转换

运算符重载

可以重载的运算符

一元操作符   +, -, !, ~, ++, --, true, false
二元操作符   +, -, *, /, %, &, |, ^, <<, >>, ==, !=, 
 >, <, >=, <=
赋值运算符 +=, -=, *=, /=, >>=, <<=, %=, &=, |=, ^=
要求同时重载的运算符
一元操作符  true和false
二元操作符  ==和!=,  >和<, >=和<=

示例:

using System;
class Complex
{
    double r, v;
    public Complex(double r, double v)
    {
        this.r = r;
        this.v = v;
    }
    //二元操作符“+”重载
    public static Complex operator +(Complex a, Complex b)
    {
        return new Complex(a.r + b.r, a.v + b.v);
    }
    //一元操作符“-”重载
    public static Complex operator -(Complex a)
    {
        return new Complex(-a.r, -a.v);
    }
    //一元操作符“++”重载
    public static Complex operator ++(Complex a)
    {
        double r = a.r + 1;
        double v = a.v + 1;
        return new Complex(r, v);
    }
    public void Print()
    {
        Console.WriteLine(r + " + " + v + "i");
    }
}
class  Test
{
    public static void Main()
    {
        Complex  a=new  Complex(3,4);
        Complex  b=new Complex(5,6);
        Complex  c=-a;
        c.Print();
        Complex  d=a+b;
        d.Print();
        a.Print();
        Complex  e=a++;
        a.Print();
        e.Print();
        Complex  f=++a;
        a.Print();
        f.Print();
    }
}
  • C#要求以静态方式声明运算符重载
  • 编译器不能改变二元运算符的参数顺序
  • C#不允许重载=运算符,如果重载+运算符, 编译器会自动使用+运算符的重载计算+=运算符的操作

不能重载的运算符:

checked和unchecked
byte b = 255;
unchecked
 {
        b++;
 }
Console.WriteLine(b.ToString());
is运算符
int i = 10;
if (i is object)
{
    Console.WriteLine("i is an object");
    Console.ReadLine();
}
as运算符

用于执行引用类型的显式类型转换
如果要转换的类型与指定的类型兼容,转换就会成功进行;如果类型不兼容,as运算符就会返回null

 object o1 = "Some String";
 object o2 = 5;
 string s1=o1 as String;
 string s2 = o2 as String;
typeof运算符

返回一个表示特定类型的System.Type对象
在使用反射动态查找对象的信息时,这个运算符很有效

用户定义的数据类型转换

隐式类型转换

public   static  implicit  operator  Square(double s)
{
     ……
} 

显式类型转换

public   static  explicit  operator  double(Square s)
{
     ……
} 

这种数据类型转换在不同结构或类之间进行是允许的,但有两个限制

  • 如果某个类直接或间接继承了另一个类,就不能在两个类之间进行数据类型转换
  • 数据类型转换必须在源或目标数据类型定义的内部定义。一旦在一个类中定义数据类型转换,就不能在另一个类中定义相同的数据类型转换
public static  implicit   operator B (A a)
{
       ……
}
using System;

class Square
{
    private double side;
    public Square(int s)
    {
        Console.WriteLine("int类型参数构造函数");
        side = (double)s;
    }
    public Square(double s)
    {
        Console.WriteLine("double类型参数构造函数");
        side = s;
    }
    //重写object类的ToString()方法
    public override string ToString()
    {
        Console.WriteLine("重写object类的ToString()方法");
        return this.side.ToString();
    }
    //重载“+”操作符,参数为两个Square类
    public static Square operator +(Square x, Square y)
    {
        Console.WriteLine("重载+操作符,参数为两个Square类");
        return new Square(x.side + y.side);
    }
    //重载“+”操作符,参数一个为Square类,一个为double类型
    public static Square operator +(Square x, double y)
    {
        Console.WriteLine("重载+操作符,参数一个为Square类,一个为double类型");
        return new Square(x.side + y);
    }
    //重载“+”操作符,参数一个为Square类,一个为int类型
    public static Square operator +(Square x, int y)
    {
        Console.WriteLine("重载+操作符,参数一个为Square类,一个为int类型");
        return x + (double)y; //调用上面的重载“+”操作符
    }
    //隐式类型转换,实现double类型转换为Square
    public static implicit operator Square(double s)
    {
        Console.WriteLine("隐式类型转换,实现double类型转换为Square");
        return new Square(s);
    }
    //隐式类型转换,实现int类型转换为Square
    public static implicit operator Square(int s)
    {
        Console.WriteLine("隐式类型转换,实现int类型转换为Square");
        return new Square(s);
    }
    //显式类型转换,实现Square类型转换为double
    public static explicit operator double(Square s)
    {
        Console.WriteLine("显式类型转换,实现Square类型转换为double");
        return s.side;
    }
    //重载“==”操作符
    public static bool operator ==(Square x, Square y)
    {
        Console.WriteLine("重载==操作符,参数为两个Square类");
        return x.side == y.side;
    }
    //重载“!=”操作符
    public static bool operator !=(Square x, Square y)
    {
        Console.WriteLine("重载!=操作符,参数为两个Square类");
        return !(x == y); //调用上面的重载“==”操作符
    }
    //当重载“==”和“!=”的同时还要重载object类的GetHashCode()和Equals(),否则编译器会出现警告
    public override bool Equals(object o)
    {
        return this == (Square)o;
    }
    public override int GetHashCode()
    {
        return (int)side;
    }
    //重载“>”操作符
    public static bool operator >(Square x, Square y)
    {
        Console.WriteLine("重载>操作符,参数为两个Square类");
        return x.side > y.side;
    }
    //重载“<”操作符
    public static bool operator <(Square x, Square y)
    {
        Console.WriteLine("重载<操作符,参数为两个Square类");
        return x.side < y.side;
    }
    //重载“<=”操作符
    public static bool operator <=(Square x, Square y)
    {
        Console.WriteLine("重载<=操作符,参数为两个Square类");
        return (x < y) || (x == y);//调用上面的重载“<”操作符和“==”操作符
    }
    //重载“>=”操作符
    public static bool operator >=(Square x, Square y)
    {
        Console.WriteLine("重载>=操作符,参数为两个Square类");
        return (x > y) || (x == y);//调用上面的重载“>”操作符和“==”操作符
    }
    public static void Main()
    {
        Square s1 = new Square(10);
        Square s2 = new Square(20);
        Square s3 = s1 + s2;
        Console.WriteLine(s3);
        Console.WriteLine(s3 + 15);
        Console.WriteLine(s3 + 1.5);
        s3 = 10;
        Console.WriteLine(s3);
        s3 = 20.8;
        Console.WriteLine(s3);
        double d = (double)s3;
        Console.WriteLine("d={0}", d);
        Square  s4 = 10;
        Console.WriteLine(s1 == s4);
        Console.WriteLine(s1 != s4);
        Console.WriteLine(s1 > s2);
        Console.WriteLine(s1 <= s4);
    }
}

你可能感兴趣的:(浅学C#)