C# 覆盖可能性

发布于 2024-10-25 00:00:47 字数 832 浏览 1 评论 0原文

我正在编写一个程序,计算 2 维空间和 3 维空间中 2 点之间的距离。

我创建了两个类“2DPoint”和“3DPoint”。 3DPoint 继承自 2DPoint。

我在 2DPoint 中有一个“calculateDistance”方法,我想在 3DPoint 中覆盖它。

这是 2DPoint 中的代码:

 public virtual double calcDistance(int xco1, int xco2, int yco1, int yco2)
 {

        .....(some maths)


            return distance;
 }

现在我遇到的问题是在 3DPoint 中,我必须输入 X、Y,然后输入 2 个点的 Z 坐标,因此通过在 3DPoint 类中声明“覆盖”,它不会让我覆盖2D 点中的方法。

例如,

public override double calcDistance(int xco1, int xco2, int yco1, int yco2, int zco1, int zco2)
 {

        .....(some maths)


            return distance;
 }

所以我有 3 个问题:

  1. 是否可以使用我编写代码的覆盖命令来覆盖 2DPoint calcDistance?
  2. 如果没有,有没有办法使用覆盖命令解决我的问题?
  3. 重载与覆盖相同吗,因为这是我能看到的唯一解决方法。

I am writing a program that calculates the distance between 2 points in 2 dimensional space and 3 dimensional space.

I have created two classes "2DPoint" and "3DPoint". 3DPoint inherits from 2DPoint.

I have a "calculateDistance" method in 2DPoint which i want to override in 3DPoint.

Here is the code in 2DPoint:

 public virtual double calcDistance(int xco1, int xco2, int yco1, int yco2)
 {

        .....(some maths)


            return distance;
 }

Now the problem im having is in 3DPoint i have to feed in X, Y and then a Z co-ordinate for 2 points and so by stating "override" in the 3DPoint class it wont let me override the method in 2D Point.

e.g.

public override double calcDistance(int xco1, int xco2, int yco1, int yco2, int zco1, int zco2)
 {

        .....(some maths)


            return distance;
 }

So I have 3 questions:

  1. Is it at all possible to override the 2DPoint calcDistance using the override command how i have written the code?
  2. If not is there a way around my problem using the override command?
  3. Is overloading the same as overriding, because that is the only way around it i can see.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

心奴独伤 2024-11-01 00:00:47

这是一个比较简单的误解。

  • 重写是更改子类中例程行为的一种方法。重写的方法具有与原始方法相同的参数。
  • 重载是指具有相同名称但参数不同的方法。编译器通过匹配参数来确定您的意思。

我看不到足够的代码来知道您的基本设计是否合理,但从表面上看,您似乎需要使用重载。

This is a relatively simple misunderstanding.

  • Overriding is a means to change behaviour of a routine in a subclass. An overridden method has the same parameters as the original.
  • Overloading is when you have methods with the same name but different parameters. The compiler works out which one you mean by matching the parameters.

I can't see enough of your code to know if your basic design is sound, but on the face of it it would seem that you need to use overloading.

三岁铭 2024-11-01 00:00:47

您不必重写 2 参数函数,只需创建一个具有 3 个参数的新函数即可。创建 3d 实例后,它将对调用源可见。通过使用 3 个参数的不同“签名”(或者甚至相同的参数数量,但类型不同),编译器将知道它应该调用哪个函数。例如:

public class Calc2d
{
   public virtual CalcDistance( int Parm1, int parm2 )
   { ... }
}

public class Calc3d : Calc2d
{
   public virtual CalcDistance( int Parm1, int parm2, int Parm3 )
   { ... }
}

在 3d 类中,CalcDistance 的两个实例都是可见的,但根据传递的参数数量来决定调用哪个实例。

You shouldn't have to override a 2-parameter function, just create a new function with the 3 parameters. When an instance of the 3d is created, it will be visible to the calling source. By having a different "Signature" of 3 parameters (or even same # of parameters, but different types), the compiler will know which function it should be calling. Ex:

public class Calc2d
{
   public virtual CalcDistance( int Parm1, int parm2 )
   { ... }
}

public class Calc3d : Calc2d
{
   public virtual CalcDistance( int Parm1, int parm2, int Parm3 )
   { ... }
}

In the 3d class, BOTH instance of the CalcDistance will be visible, but depending on how many parameters are passed will dictate which instance is invoked.

旧情别恋 2024-11-01 00:00:47

首先,您不可能创建 2DPoint3DPoint 类。接下来,我真的怀疑 3D 点是否应该继承 2D 点。

至于你的问题,

  1. 重写要求参数相同(简单地说)
  2. 不,这里没有什么可以重写的是
  3. 的,重载与重写不同

First off, you cannot possibly creaate 2DPoint and 3DPoint classes. Next, I really doubt that a 3D point should inherit from 2D point.

As for your questions,

  1. Overriding requires parameters to be identical (to put simply)
  2. No, there's nothing to override here
  3. Yes, overloading is different from overriding
—━☆沉默づ 2024-11-01 00:00:47

您不应该让 3DPoint 成为 2DPoint 的子类,因为这不是 is-a 关系。 2D 点不是 3D 点的泛化,它们只是不同,不应该继承另一个点。

顺便说一句,我不明白你的方法签名 public virtual double calcDistance(int xco1, int xco2, int yco1, int yco2)。尽管它是一个实例方法,但它仍需要点的坐标,因此始终在特定点上执行。像 public virtual double calcDistance(2DPoint other) 这样的东西对我来说更有意义。

You should not let 3DPoint be a subclass of 2DPoint as this is not a is-a relation. A 2D point is not a generalization of a 3D point, there are just different and should not inherit one from the other.

Btw, I don't understand your method signature public virtual double calcDistance(int xco1, int xco2, int yco1, int yco2). It takes coordinates of the points even though its an instance method and therefore is always performed on a specific point. Something like public virtual double calcDistance(2DPoint other) would make more sense to me.

孤者何惧 2024-11-01 00:00:47

针对您的问题的更好设计并适当使用多态性将是创建 2D 点类,该类在构造函数中接受 4 个参数(Xs 和 Ys)。然后是一个 3D 点类,它接受 6 个参数(X、Y 和 Z)。

然后您将写入 2DPoint

public virtual double calcDistance() 

和 3DPoint

public override double calcDistance() 

A better design to your problem and appropriately use polymorphism will be to create 2D point class that takes in the 4 parameter (Xs and Ys) in the constructor. Then a 3D point class that takes in 6 parameters (Xs, Ys and Zs).

You will then write in 2DPoint

public virtual double calcDistance() 

and 3DPoint

public override double calcDistance() 
怪我鬧 2024-11-01 00:00:47

1)您不能更改重写方法时采用的参数。如果您尝试这样做,您最终会在子类中得到两个可用的方法。

3) 重载是指您的方法采用不同的参数集,例如 Calc(int x)Calc(int x, int y)。这与重写不同,因为重写会更改一个类中与其基类相比的行为。

您可以执行以下操作之一:

i) 让您的方法在接口上运行。点。检查 IPoint 的类型,如果它是 2DPoint 并且您期望是 3dPoint,则抛出异常。您可以添加泛型以使其成为强类型。这可能就是我会采取的方法。它确保您调用正确的方法,并且会在编译时而不是运行时抱怨。

interface IPoint<TPoint> where TPoint : IPoint
{
   Double CalcuateDistance(TPoint point);
}

public class 2DPoint : IPoint<2DPoint>
{
   public Double X { get; set; }
   public Double Y { get; set; }
   public Double CalculateDistance(2DPoint point)
   {
      // some maths using this.X/this.Y and point.X/point.Y
   }
}

public class 3DPoint : IPoint<3DPoint>
{
   public Double X { get; set; }
   public Double Y { get; set; }
   public Double Z { get; set; }

   public Double CalculateDistance(3DPoint point)
   {
      // some maths using this.X/this.Y/this.Z and point.X/point.Y/point.Z
   }
}

使用这种方法,如果您对两种类型的点具有通用功能,则可以将其放置在抽象基类中,而不是 AbstractPoint中。 :IPoint。如果您这样做,您将定义:

abstract class AbstractPoint<TPoint> : IPoint<TPoint>
{
   public virtual double CalculateDistance(TPoint point);
}

当您在 2DPoint 和 3DPoint 中重写此设置时,您将自动传入正确类型的 TPoint :)

ii) 让您的基类方法采用 az,其默认值为 0为所有 2D 点传入 0。这与您的基础上有 2 个方法相同(一个接受 az,一个不接受,并在正确的时间调用正确的方法)

Calc(int x, int y, int z = 0);

iii) 删除继承并拥有 2 个单独的具体类。

1) You can't change the parameters that are taken when overriding methods. If you try to do this you'll end up with two methods available on your sub-class.

3) Overloading is where you have a method that takes different sets of parameters e.g. Calc(int x) and Calc(int x, int y). This is different to overriding as overriding changes the behaviour in one class compared to that of it's base class.

You could do one of a number of things:

i) Make your method operate on an interface. IPoint. Check the type of the IPoint, if it's a 2DPoint and you expected a 3dPoint then throw an exception. You can add generics to make it strongly typed. This is probably the approach I would take. It ensures that you call the correct method, and will complain at compile time rather than runtime.

interface IPoint<TPoint> where TPoint : IPoint
{
   Double CalcuateDistance(TPoint point);
}

public class 2DPoint : IPoint<2DPoint>
{
   public Double X { get; set; }
   public Double Y { get; set; }
   public Double CalculateDistance(2DPoint point)
   {
      // some maths using this.X/this.Y and point.X/point.Y
   }
}

public class 3DPoint : IPoint<3DPoint>
{
   public Double X { get; set; }
   public Double Y { get; set; }
   public Double Z { get; set; }

   public Double CalculateDistance(3DPoint point)
   {
      // some maths using this.X/this.Y/this.Z and point.X/point.Y/point.Z
   }
}

Using this approach, if you had common functionality to both types of point you could place that in a base abstract class instead AbstractPoint<TPoint> : IPoint<TPoint>. If you did it this way you would define:

abstract class AbstractPoint<TPoint> : IPoint<TPoint>
{
   public virtual double CalculateDistance(TPoint point);
}

When you override this in 2DPoint and 3DPoint then you will automatically have the correct type of TPoint being passed in :)

ii) Make your base class method take a z, which has a default value of 0. Just pass in 0 for all 2D points. This is the same as having 2 methods on your base (one that takes a z, ones that doesn't and calling the right one at the right time)

Calc(int x, int y, int z = 0);

iii) Remove the inheritance and have 2 separate concerete classes.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文