0

I am very new to C#, but have to use it for a project at work, so I apologize if this is a duplicate, use the wrong vocabulary or am asking a simple question (it is hard to research a question when you don't understand what the question should be).

I have a class with multiple constructors. I want the properties of that class to be based on the constructor that I call. This is the code I have now:

public class MyClass
{
    public object Property1;
    public object Property2;
    public object Property3;

    public MyClass(object newProperty1, object newProperty2, object newProperty3)
    {
        Property1 = newProperty1;
        Property2 = newProperty2;
        Property3 = newProperty3;
    }

    public MyClass(object newProperty1, object newProperty2)
    {
        Property1 = newProperty1;
        Property2 = newProperty2;
    }

}

What happens is when I call the second constructor is I get an empty Property3 object. What I want to have happen is that there is no Property3 object property included in MyClass at all when the second constructor is called.

Is this possible? Thanks in advance for the help.

2
  • Those are not properties, those are fields, properties would be declared like public object Property1 {get; set;} Commented Jul 14, 2015 at 18:40
  • If I understood correctly you just want to delete the field of an instance, as it's possible with javascript? Commented Jul 14, 2015 at 18:45

4 Answers 4

2

No, this isn't possible.

Fields are compile-time properties of a class, not runtime. During runtime, you can't change how many and what types of variables a class stores (although you can certainly change their values).

Sign up to request clarification or add additional context in comments.

8 Comments

I know that C# has an automatic garbage collecting, so is there any way that I could force the garbage collector to delete the empty object after the second constructor runs?
@cmbrooks what empty object? Property3 will be null - there is nothing to clean up.
Maybe I used the wrong vocab. Is there a way to tell the gc to delete it at all?
Not sure here, but I think that if you did that, the only thing you would do is to release the memory block for "property3" which, as others have said, start as null. If it is true, that part of the memory could be used to store any value which your program may try to read.
@MVCDS, no, if you could delete a reference it does not "cascade" up, that would be a recipe for disaster because it could possibly cascade up the entire ownership chain. In all reality forcing the GC to do something usually means you are doing it wrong, the GC will clean up resources when they are marked and swept, this is a good read: msdn.microsoft.com/en-us/library/ee787088(v=vs.110).aspx
|
2

You should use inheritance for what you are trying to accomplish.

public class MyClass
{
    public object Property1;
    public object Property2;

    public MyClass(object newProperty1, object newProperty2)
    {
        Property1 = newProperty1;
        Property2 = newProperty2;
    }

}

public class MyClass2 : MyClass
{
    public object Property3;

    public MyClass2(object newProperty1, object newProperty2, object newProperty3)
               :base(newProperty1, newProperty2)
    {
        Property3 = newProperty3;
    }
}

2 Comments

You where not calling the base constructor correctly, I corrected your code, if you want you can roll it back and make whatever corrections you want.
Thanks! I will try and pay more attention next time.
1

It is kind of possible to do what you are asking, but you lose the ability to use intellisense (at least as of VS2013):

public class MyClass : DynamicObject
{
    private Dictionary<string, object> _dynamicMembers = new Dictionary<string, object>();

    public MyClass(object newProperty1, object newProperty2, object newProperty3)
       : this(newProperty1, newProperty2)
    {
        ((dynamic)this).NewProperty3 = newProperty3;
    }

    public MyClass(object newProperty1, object newProperty2)
    {
        ((dynamic)this).NewProperty1 = newProperty1;
        ((dynamic)this).NewProperty2 = newProperty2;
    }

    public override IEnumerable<string> GetDynamicMemberNames()
    {
        return _dynamicMembers.Keys.ToArray();
    }

    public override bool TryGetMember(GetMemberBinder binder, out object result)
    {
        return _dynamicMembers.TryGetValue(binder.Name, out result); 
    }

    public override bool TrySetMember(SetMemberBinder binder, object value)
    {
        _dynamicMembers[binder.Name] = value;

        return true;
    }
}

Which is then used like:

dynamic threePropertyClass = new MyClass(10, "something", 1.6f);
dynamic twoPropertyClass = new MyClass(10, "something");

However there is a lot of boxing/unboxing going on here and I'd avoid it as much as possible. The MyClass object really doesn't have the properties you are trying to reference, it loads them from a Dictionary<string, object>, but it does work like you are wanting, only containing the properties you want. You can also add new properties by doing something like:

threePropertyClass.NewProperty = 15.2;

And you could add additional logic in the TrySetMember to keep the user from doing that if you didn't want that.

Comments

0

Your declaration is equivalent to :

public class MyClass
{
    public object Property1 = null ;
    public object Property2 = null ;
    public object Property3 = null ;

As you can see, Property3 is null by default. Then no need to dispose Property3.

Remark: you can refactor your second constructor like this:

 public MyClass(object newProperty1, object newProperty2) : this(newProperty1,newProperty2,null) {}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.