作为一项技术练习,我试图创建不同的方法来计算三角形周长。
当给出三条边时 - 任务很简单, 但是当我们得到两条边和它们之间或一条边和它的两条边之间的角度时 - 我们应该应用一些三角函数操作。
为了区分这三种情况,我将边缘称为小数,将角度称为浮点数,从而为系统提供了一个提示哪种方法可以过载(例如:十进制和放大&十进制=> 2边缘和一个角度)。
这不是最优雅的解决方案,因为不应该使用数据类型来传输信息。 另一种选择是添加另一个变量,它将获得值1或2或3作为指示它是什么类型的问题,但在这种情况下不需要重载..
有没有办法创建三个重载方法,每个方法获得三位小数,并以某种方式添加三个变量符号化的指示(以及使用哪种方法)?
答案 0 :(得分:1)
使用不同类型是正确的方法。使用decimal
和float
是错误的方法。您应该已经创建了两个(不可变的)struct Length
和Angle
,可以显式地转换为decimal
/ double
。
public struct Length
{
public readonly decimal Value;
public Length(decimal length)
{
Value = length;
}
public override int GetHashCode()
{
return Value.GetHashCode();
}
public override bool Equals(object obj)
{
if (obj == null || !(obj is Length))
{
return false;
}
return Value == ((Length)obj).Value;
}
public override string ToString()
{
return Value.ToString();
}
public static explicit operator Length(decimal value)
{
return new Length(value);
}
public static explicit operator decimal(Length length)
{
return length.Value;
}
public static Length operator+(Length length1, Length length2)
{
return new Length(length1.Value + length2.Value);
}
}
public struct Angle
{
public readonly decimal Value;
public Angle(decimal angle)
{
Value = angle;
}
public override int GetHashCode()
{
return Value.GetHashCode();
}
public override bool Equals(object obj)
{
if (obj == null || !(obj is Angle))
{
return false;
}
return Value == ((Angle)obj).Value;
}
public override string ToString()
{
return Value.ToString();
}
public static explicit operator Angle(decimal value)
{
return new Angle(value);
}
public static explicit operator decimal(Angle angle)
{
return angle.Value;
}
public static Angle operator +(Angle angle1, Angle angle2)
{
return new Angle(angle1.Value + angle2.Value);
}
}
public static Length Perimeter(Length length1, Length length2, Length length3)
{
return length1 + length2 + length3;
// Or
//return new Length(length1.Value + length2.Value + length3.Value);
}
使用:
Length length1 = (Length)1.0m;
Length length2 = (Length)2.0m;
Length length3 = (Length)3.0m;
Length perimeter = Perimeter(length1, length2, length3);
一些注意事项:
我已在operator+
/ Length
内Angle
实施Length
Length
和Angle
Angle
}})。
命名很糟糕。我会称他们为Meters
和Radians
。
可以轻松添加其他运算符(可能operator-
可能有用)和接口(IComparable
,IComparable<>
,IEquatable<>
,{{1} },IFormattable
)和其他运算符(ISerializable
,==
,!=
...)。
如果您将结构重命名为<=
和Meters
,请更改Radians
以打印度量单位。
答案 1 :(得分:-1)
使用命名参数并将第三个参数实现为可选参数。请参阅here。