Understand that Override and New Keywords can help to either implement the base methods or the child methods. But when using the real time examples, I don't see any virtual methods in the following project. Can someone help me to understand why
virtaul
was not used for theBeginTran
method in theServiceBase
Class.- And if making
virtual
base method and usingnew
in derived class implements the base method why there is a call for thebase.BeginTran()
explicitly.
Please help to clarify the doubts.
public sealed class SearchService : ServiceLogic
{
public new SearchService BeginTran()
{
base.BeginTran();
return this;
}
public abstract class ServiceLogic : ServiceBase
{
}
public abstract class ServiceBase : IDisposable
{
public void BeginTran()
{
this.proxy.GetContext().BeginTran();
}
}
Also, the following is my Controller code
using (var svc = new SearchService())
{
return svc.getAll();
}
Calling the Web Service
public sealed class SearchService: ServiceLogic
{
public new SearchService BeginTran()
{
base.BeginTran();
return this;
}
public SearchService Delete(Guid id)
{
Let<User>().Delete(id);
return this;
}
public User GetAll(Guid id)
{
}
So I would like to know why there was a need to call the BeginTran
and return another object of a sealed SearchService
class as earlier we did create an instance using var svc = new SearchService()
.
CodePudding user response:
Override/Virtual and New actually solve two different problems and have two different uses.
Here is an example of virtual/override. Where the base class and the child class both return the exact same type (void).
public abstract class ServiceBase
{
public virtual void BeginTran()
{
base.BeginTran();
}
}
public sealed class SearchService : ServiceBase
{
public override void BeginTran()
{
base.BeginTran();
}
}
However, notice in your example using new
you have this :
public sealed class SearchService : ServiceBase
{
public new SearchService BeginTran()
{
base.BeginTran();
return this;
}
}
Your return type is now SearchService, not void. Because you have changed the return type, you can't "Override" the method, you need to use the new keyword to return a different type. This is called method "hiding".
There is also other side effects to this. Essentially the two methods are not connected, so polymorphism can often completely break and do unexpected things.
I would personally say that method hiding, or using the new keyword is a direct contradiction of the Liskov Principle which says that types can be replaced by subtypes without altering the program. In your case, that would not be true if you change the return type. Bit more info on that here : https://dotnetcoretutorials.com/2019/10/20/solid-in-c-liskov-principle/
In 15 years of C# experience, I have used the new keyword maybe a handful of times, and almost always when trying to override a library method and bastardize the code.
CodePudding user response:
When you do public new SearchService BeginTran()
you are not creating anything. That isn't creating an instance of the class. That new
is the same word that you use to create instances but here has another meaning: change the signature of a method or override a non virtual method in base class.
The unique instance that you create is this one:
using (var svc = new SearchService())
Sometimes, when you control the method to call, you can create another method and use it instead of override with new
keyword. For example:
public sealed class SearchService : ServiceLogic
{
public SearchService StartTran()
{
base.BeginTran();
return this;
}
You can't do this when the invocation it's done in some method of the base class, called indirectly. In that case, you must override that method. But in this case, you can simply create another method.