How can I override the base class operator == so the call is redefined

With code as below

public class Task { string Name; public static bool operator ==(Task t1, Task t2) { return t1.Name = t2.Name && t1.GetType() == t2.GetType(); } } public class TaskA : Task { int aThing; public static bool operator ==(TaskA t1, TaskA t2) { return (Task)t1 == (Task)t2 && t1.GetType() == t2.GetType() && t1.aThing == t2.aThing; } } public class TaskB : Task //more of the same class Stuffin { List<Task> Tasks; void CheckIt() { bool theSame = Tasks[0] == Tasks[1]; } 

I am trying to make sure that the derived statement (TaskA. ==) is being called.

I get a compilation error when using the method here .

I think I can make it work correctly if the statement was not static, because I could then override the base class operator. Is it possible?

As soon as I get this, how would I compare the basic properties (I think casting to the type of the task [(Task) t1 == (Task) t2] will not work)?

+4
source share
5 answers

My hybrid solution that seems to work.

 public class Task { string Name; public static bool operator ==(Task t1, Task t2) { if ((object)t1 == null || (object)t2 == null) { return (object)t1 == null && (object)t2 == null; } return t1.Name == t2.Name && t1.GetType() == t2.GetType(); } public virtual bool Equals(Task t2) { return this == t2; } } public class TaskA : Task { int aThing; public static bool operator ==(TaskA t1, TaskA t2) { if ((object)t1 == null || (object)t2 == null) { return (object)t1 == null && (object)t2 == null; } return (Task)t1 == (Task)t2 && t1.aThing == t2.aThing; } public override bool Equals(Task t2) { return this == t2 as TaskA; } } 
0
source

You can not. Operators are not overridden; they are overloaded. This means that the implementation to be used will be fully resolved at compile time.

One thing you can do is override Equals in Task and call it from == , and then redefine it in TaskA . It also makes it easier to check for "basic properties" - just call base.Equals from TaskA.Equals .

+8
source

What you are trying to do is really complicated in C #. Basically, you want a statement whose behavior is determined at runtime based on the runtime types of both arguments. It's complicated; the == operator is dispatched based on the compilation time types of both operands, and the .Equals method is dispatched based on the receiver's runtime type, but the argument compilation time type.

The standard way to implement dual sending in a language that supports only one virtual sending is the visitor template. You can look at it.

For further reading on this subject, you can read my article here:

http://blogs.msdn.com/b/ericlippert/archive/2009/04/09/double-your-dispatch-double-your-fun.aspx

+5
source

This post was about C ++. Consider the operator as a static function. You cannot overload it.

But you can declare a virtual instance method and call it inside your statement. But the note operator takes two arguments, and they can have a different actual type, so you need to decide how to choose one argument from the two.

 public class Task { public virtual bool MyMethod(Task anotherTask) { return true; } public static bool operator==(Task t1, Task t2) { return t1 == null ? false : t1.MyMethod(t2); } } public class TaskA { public override bool MyMethod(Task anotherTask) { return false; } } 
+2
source

If you can make the task an abstract class, a template template template can be nice.

 public abstract class Task { string Name; protected abstract bool DoEquals( Task rhs ); public static bool operator ==(Task t1, Task t2) { return t1.DoEquals( t2 ); } } public class TaskA : Task { protected bool DoEquals( Task rhs ) { return /* custom compare */ } } public class TaskB : Task { protected bool DoEquals( Task rhs ) { return /* custom compare */ } } 
+1
source

Source: https://habr.com/ru/post/1313923/


All Articles