Can we interrupt creating an object in constructor - c#

Could you help me please.
I have one idea but don't know how can I implement it.
So the question is:
Can we interrupt creating an object in constructor
i.e.
//Code
SomeClass someClass = new SomeClass(someCriteria);
So if someCriteria doesn't answer on our requirements we shouldn't create an object and should return null, instead of new object.
Is it possible to implement it in C#?

Best way is a factory class but if your class is so small you can use this:
class SomeClass
{
private string _someCriteria;
private SomeClass(string someCriteria)
{
_someCriteria = someCriteria;
}
public static SomeClass CreateInstance(string someCriteria)
{
if (someCriteria.Length > 2)
{
return new SomeClass(someCriteria);
}
return null;
}
}
class Program
{
static void Main(string[] args)
{
// returns null
SomeClass someClass = SomeClass.CreateInstance("t");
// returns object
SomeClass someClass2 = SomeClass.CreateInstance("test");
}
}

You may want to use a factory class that creates instances of SomeClass returning null if the someCriteria is invalid.

It is quite usual that you check the constructor parameters if they are valid. If not, you usually throw an exception.
I also read a nice advice to provide static methods for validating constructor parameters. This enables the user of your class to check if whatever he is going to pass in the constructor will succeed or not. Those who are certain the parameters are ok (they made some sort of their validation) will go directly with the constructor.
Also consider what the user of your class will possibly do with null instead of the object (if some sort of factory class was used). Would this typically result in an NullPointerException on the next line? It's usually good idea to stop the wrong things as soon as possible, in this case throw the exception and finish. It is cleaner solution than returning null and if someone really wants to (this definetly won't be best practise) he can still catch this exception ...

If the parameters to your constructor are invalid, consider throwing ArgumentException or one of its descendant classes (e.g. ArgumentOutOfRangeException).

The new construct guarantees that an object will be returned (or an exception thrown). So as bleeeah recommended, a factory or similar concept will allow you to apply your logic.

That would be possible. Another way would be to put your checking in before you create the object. Like so
SomeClass someClass = null;
if (someCriteria == VALID)
{
someClass = new SomeClass(someCriteria);
}
Hope this helps.

No it is not possible directly.
You could throw an exception and add the required code to check for the exception and assign null to you variable.
A better solution would be to use a Factory that would return null if some condition fail.
var someClass = SomeClassFactory.Create(someCriteria);
if(someClass != null)
{
}

Related

Not sure what the System.NullRefrenceException is trying to tell me [duplicate]

This question already has answers here:
What is a NullReferenceException, and how do I fix it?
(27 answers)
Closed 8 years ago.
I am receiving this error and I'm not sure what it means?
Object reference not set to an instance of an object.
Variables in .NET are either reference types or value types. Value types are primitives such as integers and booleans or structures (and can be identified because they inherit from System.ValueType). Boolean variables, when declared, have a default value:
bool mybool;
//mybool == false
Reference types, when declared, do not have a default value:
class ExampleClass
{
}
ExampleClass exampleClass; //== null
If you try to access a member of a class instance using a null reference then you get a System.NullReferenceException. Which is the same as Object reference not set to an instance of an object.
The following code is a simple way of reproducing this:
static void Main(string[] args)
{
var exampleClass = new ExampleClass();
var returnedClass = exampleClass.ExampleMethod();
returnedClass.AnotherExampleMethod(); //NullReferenceException here.
}
class ExampleClass
{
public ReturnedClass ExampleMethod()
{
return null;
}
}
class ReturnedClass
{
public void AnotherExampleMethod()
{
}
}
This is a very common error and can occur because of all kinds of reasons. The root cause really depends on the specific scenario that you've encountered.
If you are using an API or invoking methods that may return null then it's important to handle this gracefully. The main method above can be modified in such a way that the NullReferenceException should never be seen by a user:
static void Main(string[] args)
{
var exampleClass = new ExampleClass();
var returnedClass = exampleClass.ExampleMethod();
if (returnedClass == null)
{
//throw a meaningful exception or give some useful feedback to the user!
return;
}
returnedClass.AnotherExampleMethod();
}
All of the above really just hints of .NET Type Fundamentals, for further information I'd recommend either picking up CLR via C# or reading this MSDN article by the same author - Jeffrey Richter. Also check out, much more complex, example of when you can encounter a NullReferenceException.
Some teams using Resharper make use of JetBrains attributes to annotate code to highlight where nulls are (not) expected.
In a nutshell it means.. You are trying to access an object without instantiating it.. You might need to use the "new" keyword to instantiate it first i.e create an instance of it.
For eg:
public class MyClass
{
public int Id {get; set;}
}
MyClass myClass;
myClass.Id = 0; <----------- An error will be thrown here.. because myClass is null here...
You will have to use:
myClass = new MyClass();
myClass.Id = 0;
Hope I made it clear..
Another easy way to get this:
Person myPet = GetPersonFromDatabase();
// check for myPet == null... AND for myPet.PetType == null
if ( myPet.PetType == "cat" ) <--- fall down go boom!
Not to be blunt but it means exactly what it says. One of your object references is NULL. You'll see this when you try and access the property or method of a NULL'd object.
It means you did something like this.
Class myObject = GetObjectFromFunction();
And without doing
if(myObject!=null), you go ahead do myObject.Method();
If I have the class:
public class MyClass
{
public void MyMethod()
{
}
}
and I then do:
MyClass myClass = null;
myClass.MyMethod();
The second line throws this exception becuase I'm calling a method on a reference type object that is null (I.e. has not been instantiated by calling myClass = new MyClass())
Most of the time, when you try to assing value into object, and if the value is null, then this kind of exception occur.
Please check this link.
for the sake of self learning, you can put some check condition. like
if (myObj== null)
Console.Write("myObj is NULL");
what does this error mean? Object reference not set to an instance of an object.
exactly what it says, you are trying to use a null object as if it was a properly
referenced object.

Determine if an object has a property (set to null or anything else) [duplicate]

Using dynamic pattern perhaps? You can call any method/property using the dynamic keyword, right? How to check whether the method exist before calling myDynamicObject.DoStuff(), for example?
You could write something like that :
public static bool HasMethod(this object objectToCheck, string methodName)
{
var type = objectToCheck.GetType();
return type.GetMethod(methodName) != null;
}
Edit : you can even do an extension method and use it like this
myObject.HasMethod("SomeMethod");
via Reflection
var property = object.GetType().GetProperty("YourProperty")
property.SetValue(object,some_value,null);
Similar is for methods
It is an old question, but I just ran into it.
Type.GetMethod(string name) will throw an AmbiguousMatchException if there is more than one method with that name, so we better handle that case
public static bool HasMethod(this object objectToCheck, string methodName)
{
try
{
var type = objectToCheck.GetType();
return type.GetMethod(methodName) != null;
}
catch(AmbiguousMatchException)
{
// ambiguous means there is more than one result,
// which means: a method with that name does exist
return true;
}
}
Wouldn't it be better to not use any dynamic types for this, and let your class implement an interface.
Then, you can check at runtime wether an object implements that interface, and thus, has the expected method (or property).
public interface IMyInterface
{
void Somemethod();
}
IMyInterface x = anyObject as IMyInterface;
if( x != null )
{
x.Somemethod();
}
I think this is the only correct way.
The thing you're referring to is duck-typing, which is useful in scenarios where you already know that the object has the method, but the compiler cannot check for that.
This is useful in COM interop scenarios for instance. (check this article)
If you want to combine duck-typing with reflection for instance, then I think you're missing the goal of duck-typing.
To avoid AmbiguousMatchException, I would rather say
objectToCheck.GetType().GetMethods().Count(m => m.Name == method) > 0

Which approach for kind of Singleton is better?

My program instantiates an object with parameters passed in command line. I need to be able to instantiate an object with those parameters but yet it should be created only once. I've read these posts 1 & 2 but I still didn't understand which approach is better:
1 - var myInstance = MyClass.Instance.Create("param1", "param2");
OR
2 - var myInstance = MyClass.Instance;
myInstance.setParam1("param1");
myInstance.setParam2("param2");
In the first approach the new instance for each different pair of parameters passed to Create will be created. The only way to prevent this is to set flag inside Create that will return the created instance.
In 2nd approach the problem is what if constructor of MyClass will depend on param1 and param2?
So, what would you suggest?
You can use the first approach too:
MyClass.Instance.Create("param1", "param2")
with slight difference, which may make parameters not mandatory, if you need, using Named Parameters, like say:
MyClass.Instance.Create(param1 = "param1", param2 = "param2")
So you can avoid using parameters at all (during call) and lay on default values provided in declaration.
I'd:
create an immutable Config class with a public constructor that takes the parameters
create a static method Config ParseCommandLine(string) that turns a command-line into a Config object.
Since this is a pure function (no side-effects, no global state) it's easy to test this.
a static method Config ParseCommandLine() that gets the actual command line and calls the above method (a bit ugly, since it accesses global mutable state)
Finally use Config.SetInstance(ParseCommandLine()) to back the Instance property on your "singleton". This is a bit ugly, but using a singleton is ugly in the first place.
This "singleton" doesn't really enforce that there is a single config, but it's more of a default instance. In my experience real singletons are rarely needed, and even the default instance is kind of a hack.
You'd end up with something like this:
public class Config
{
public string Param1{get;private set;}
public int Param2(get;private set;}
public Config(string param1, int param2)
{
Param1=param1;
Param2=param2;
}
// take a string[] if you prefer to use Environment.GetCommandLineArgs
public Config ParseCommandLine(string commandLine)
{
string param1=...;
int param2=...;
return new Config(param1:param1, param2:param2);
}
public Config ParseCommandLine()
{
return ParseCommandLine(Environment.CommandLine);
}
}
I'd also consider throwing the static Instance property away, in favour of injecting the configuration to the objects that need it. But for a small program that may be over-engineering.
In your case it is better to use no Singleton.
Singleton's Intent:
Ensure that only one instance of a class is created.
Provide a global point of access to the object.
http://www.oodesign.com/singleton-pattern.html
Use a private static attribute as a flag if you need to ensure that only one instance is allowed.
Update:
public class MyClass {
private static boolean isAlreadyInitiated = false;
public MyClass() {
if(isAlreadyInitiated){
throw new IllegalStateException("Only one instance allowed.");
}
isAlreadyInitiated = true;
}
}

How to avoid using the is operator in c# when my method returns a base type?

I have an abstract base class P. I have two classes that inherit P called I and O.
I have a Get() method in my repository that returns P. This method always returns an instance of either I or O depending on a value.
public P Get(string pci)
{
var a = GetAByPCI(string pci);
if(a == 1)
return new I();
else if(a == 2)
return new O();
else
// throw exception here.
}
When I call this method from another location I need to check and cast the type.
P p = PRepository.Get("200");
if(p is I)
I i = (I)p;
I'd like to avoid having to check and downcast every time p above is used. I feel as though I'm doing some fundamentally wrong here, but am not certain.
Update:
The derived types I & O have additional properties that need to be used but only pertain to that specific type. P has many abstract properties that are implemented in inheriting types. Downcasting is the only way I can get to the concrete types as needed?
Maybe the logic is entirely wrong.
The whole point of having a base class is to avoid having to deal with the subclass itself. Just add an abstract method to the base class and have it implemented in the sub-classes. This way, the calling code will simply call the method without having to do any casts. This is basic polymorphism.
What is your intention? It seems you are not making proper use of inheritance.
If you return a P object from your methods, you either need to downcast or return the derived types.
You are correct to be suspect of down casting.
I would look at the template method design pattern. If you have a base class it should be used to hide the details of the subclass.
So maybe you have a method in your base class called Execute(). Inside the base class the execute method calls some protected methods, lets say Method1(), and Method2(). Method 1 would contain the shared code, method two would be abstract and the child classes would have to execute it. Then when you get your instance back you just call Execute. The proper Method2() will run without you having to cast downward.
public abstract class MyBaseClass
{
public void DoSomething()
{
//Here's a bunch of stuff I have to do everytime
DoSomethingTypeSpecific();
//I could do more stuff if I needed to
}
protected abstract void DoSomethingTypeSpecific();
}
class MyBaseClassOne : MyBaseClass
{
protected override void DoSomethingTypeSpecific()
{
Console.WriteLine(1);
}
}
class MyBaseClassTwo : MyBaseClass
{
protected override void DoSomethingTypeSpecific()
{
Console.WriteLine(2);
}
}
I would also think about using the Decorator pattern and composition instead of using inheritance.
Nevertheless you still need a cast if you want to access the properties that are not part of the base class.
If all above solutions not fitting your requirements and you don't want to change the base class (adding properties from derrived classes) then you should also think not only about your inheritance design as mentioned by most comments... you should also look for your factory/repository implementation. Is this repository doing the thing you need? Why not add a GetI() and GetO()?
For eample Linq allows you to query and filter a List with using .OfType and you get only elements of Type T.
You can add a specific Get Method with type info (e.g. with generics as I did in my example) and an additional condition.
public T Get<T>(string pci, int c)
{
var a = GetAByPCI(string pci);
if(a == c)
return new T();
else
// throw exception here.
}
Call the method Get with the generic param. The problem of this solution here is that you need to know the condition at the call time and this does not handle "special constructions" (e.g. constructor with params for T). Anyway this could be solved with the factory pattern, too.
I i = PRepository<I>.Get(1, "200"); // create a new I(), only if 1 fits GetAByPCI()
O o = PRepository<O>.Get(2, "123"); // create a new O(), only if 2 fits GetAByPCI()
// can do anything with the concrete type
You could also move the condition out of the repository/factory call with the strategy pattern (already mentioned in my answer above).
It is also possible to wrap up the "as" behind the generic method (I show you how even if I would not recommend it in most cases).
public T Get<T>(string pci)
{
return this.Get(pci) as T; // your method with trying to cast to concrete type
}
This way you can get the implementation as follows:
I i = PRepository<I>.Get("200");
if (i != null)
{
// do I specific tasks
}
It is not possible to eleminate the cast without putting the properties into the base class but you can use the strategy pattern to decouple the object creation (see my question and answer here for an example how to do this). The example shows how to decouple the switch-case but you can do the same thing with the strategy pattern for analysing the result of the context, so you can hide the cast.
public static class A
{
// please note: some example in related to your question
// and the strategy pattern provided at the link
public static P GetI(int a)
{
if (a == 1)
return new I();
else
return null; // <- this is important for evaluation
}
// can put this method anywhere else, also into another class
public static P GetO(int a)
{
if (a == 2)
return new O();
else
return null; // <- this is important for evaluation
}
public static bool Condition(string pci)
{
return !string.IsNullOrEmpty(pci); // could eval different states, values
}
}
Then it is possible to divide the as/is logic into separate methods/classes and the calling class (e.g. controller, client) doesn't need to know all the different specializations.
The following code shows how to create the context. See my posting here for the implementation details of Strategy and Context class.
var strategyI = new Strategy<int, P>(A.Condition, A.GetI);
var strategyO = new Strategy<int, P>(A.Condition, A.GetO);
var strategies = new List<Strategy<int, P>> {strategyI, strategyO};
var context = new Context<int, P>(strategies.ToArray());
var result = context.Evaluate(1); // should return a new I(), with 2 as param a new O()
// once you get the result you can create a new context to work with the result
var strategyWorkI = new Strategy<P, P>(Condition, WorkWithI);
var stragegiesForWork = new List<Strategy<P, P>> {strategyWorkI} // could be more than one
var workContext = new Context<P, P>(strategiesForWork.ToArray());
var p = workContext.Evaluate(result); // does the right thing, but
// no need to know class I here (only P)
if (p == null)
// seems to be something went wrong, throw? ...
And here is the decoupling for the cast but you still need a cast at this point.
public static P WorkWithI(P p)
{
var i = p as I; // I would prefer as instead of is (see boxing/unboxing in .net)
if (i != null)
{
// do what you want with concrete class I in i
}
return i; // <- this is important for Evaluation
}
Anyway... there is still Point in the code with an is/as, but it does not influence your controller / manager etc. (keeps code flexible and pluggable, e.g. via Dependency Injection)
... I can provide a full example if you can't understand my short description.

The type parameter cannot be used with type arguments

I wanted to code a helper method in Unit test project, which will initialize the presenter set the views instance to it and set the presenter state.
It threw me the exception:
the type parameter cannot be used with type arguments
Code:
public static **TPresenter<TView>** Initialize<TPresenter,TView>()
where TPresenter: BasePresenter<TView>, new()
where TView : new()
{
}
After couple of minutes I found the issue was with my return type TPresenter<Tview>
I read few posts which didn't clearly explain Why I'm not be able to say T1<T2>
I was forced to make the presenter assignment through reference parameter. Any explanations are welcome!
Basically there's no way of saying that a type parameter is itself a generic type with a particular number of type parameters - which you need to be able to do in order to make TPresenter<TView> make sense.
It's not clear what you mean by making it work via a reference parameter - whatever type you used for that ref parameter should be fine as a return type too. My guess is that it was just of type TPresenter, not TPresenter<TView>.
There is no such thing as a TPresenter<TView> it is meaningless. TPresenter is just a placeholder, until it is constrained by the where it could be anything, e.g. there is no int<tview> so you can't have that. Once you add the constraint it means it has to be a BasePresenter<TView> or some derived type so it will always be a Something<TView> so again TPresenter<TView> is meaningless.
This is an old one, but I hit it too. In the Class definition, just use the single type, then multiple types where you use it. E.g:
public class Template1<T>{}
void SomeFunc()
{
<Template1<SomeClass1,SomeClass2>> someValue = new <Template1<SomeClass1,SomeClass2>>()
}
//or even:
void SomeOtherFunc<U,V>()
{
<Template1<U,V>> someValue = new <Template1<U,V>>();
}
I was getting similar error in my code. #Jon Skeet correctly points to the right direction. The return type is already generic, as specified by TPresenter : BasePresenter<TView>. So we can simply use it as TPresenter instead of TPresenter<TView>.
public class BasePresenter<T>
{
}
public class Demo
{
public static TPresenter Initialize<TPresenter, TView>() where TPresenter: BasePresenter<TView>, new()
{
return null;
}
}
Small addition, I came here because i was trying to write an extension method;
public static T AutoJoinGroup<T, TD>(this T<TD> groupHubClientBase, string groupName)
where T : GroupHubClientBase<TD>
{
...
}
As you can see, I tried to use T<TD> which is incorrect, you can just use T

Categories