C#: Multiple Dynamic Properties on a Class Either Defined or with Generics

Using the class indexer of C# (abc[ xxx ] = yyy) we can create a class which has multiple dynamic properties associated by a string or whatever we want as the key for access. In the example below we use a string as our access key and holds a string as a value. The storage is accomplished by using a dictionary. See the Usage method below on how to access it.

public class MultipleDynamicProperties
{

    private Dictionary<string, string> _dynamicProperties = new Dictionary<string, string>();    
    
    // Index the data here  
    public string this[string key]
    {
        get
        {
            if ( _dynamicProperties.ContainsKey( key ) == false )
                _dynamicProperties.Add( key, string.Empty );

            return _dynamicProperties[key];
        }
        set
        {
            if ( _dynamicProperties.ContainsKey( key ) == false )
                _dynamicProperties.Add( key, value );
            else
            {
                _dynamicProperties[key] = value;
            }
        }
    }

    /// <summary>
    /// Example don't use in your code.
    /// </summary>
    public static void Usage()
    {
        MultipleDynamicProperties mdc = new MultipleDynamicProperties();

        mdc["Jabber"] = "1st Attempt";
        mdc["Jabber"] = "Wocky";
        mdc["Omega"] = "Man";

        Console.WriteLine("Jabber: " + mdc["Jabber"]); // Printers Jabber: wocky

    }

}

Using other index types say integer or enum, we can accomplish the same goal by changing or adding to our index’able properties of the class. We could have multiple accessors as long as the key is not the same. Below is an example using an enum as the key and a List<string> as the value returned:

public class MultipleDynamicPropertiesWithEnum
{
    public enum Operation
    {
        TargetA,
        TargetB,
    }

    private Dictionary<Operation, List<string>> _dynamicProperties = new Dictionary<Operation, List<string>>();


         // Index the data here  
    public List<string> this[Operation key]
    {
        get
        {
            if ( _dynamicProperties.ContainsKey( key ) == false )
                _dynamicProperties.Add( key, new List<string>() );

            return _dynamicProperties[key];
        }
        set
        {
            if ( _dynamicProperties.ContainsKey( key ) == false )
                _dynamicProperties.Add( key, value );
            else
            {
                _dynamicProperties[key] = value;
            }
        }
    }

    public static void Usage()
    {
        MultipleDynamicPropertiesWithEnum show = new MultipleDynamicPropertiesWithEnum();

        show[Operation.TargetA] = new List<string>() { "Jabber" };
        show[Operation.TargetB] = new List<string>() { "Wocky" };

        // Prints Jabberwocky 
        Console.WriteLine( show[Operation.TargetA][0] + show[Operation.TargetB][0] );
    }
}

 

Generic Option

But why limit ourselves, why not make the accessor generic, so the user/consumer can dictate what the keys and what data is returned. Here is the generic version where we mimic the hard coded version of string and string.

/// <summary>
/// This class has a generic indexor defined by the generic parameters specified
/// by the consumer.
/// </summary>
/// <typeparam name="KY">Key type to use to acces the value type to store.</typeparam>
/// <typeparam name="T">The value type to store.</typeparam>
/// <remarks>See Usage on how to use.</remarks>
public class MultipleDynamicPropertiesAsGeneric<KY, T>
{

    private Dictionary<KY, T> _dynamicProperties = new Dictionary<KY, T>();

    // Index the data here  
    public T this[KY key]
    {
        get
        {
            if ( _dynamicProperties.ContainsKey( key ) == false )
            {
                _dynamicProperties.Add( key, Activator.CreateInstance<T>() );
            }

            return _dynamicProperties[key];
        }
        set
        {
            if ( _dynamicProperties.ContainsKey( key ) == false )
                _dynamicProperties.Add( key, value );
            else
            {
                _dynamicProperties[key] = value;
            }
        }
    }

    public static void Usage()
    {
        MultipleDynamicPropertiesAsGeneric<string, string> show = new MultipleDynamicPropertiesAsGeneric<string, string>();

        show["Jabber"] = "Wocky";

        // Prints wocky 
        Console.WriteLine( show["Jabber"] );

    }

}
Share

8 Comments

  1. Omer Mor says:

    What is the difference between MultipleDynamicPropertiesAsGeneric and a standard generic Dictionary? The dictionary also exposes its values through an indexer.

  2. Brian says:

    Is there a way you can bind a list of MultipleDynamicProperties objects to a GridView?

    • OmegaMan says:

      You would have to specify the bindings depending on what grid we are talking about asp.net, silverlight/wpf or winforms. Post your question to the MSDN or asp.net forums for a better answer depending on which you are using.

  3. Manu Parashar says:

    Thats a good code snippet for unknown number of properties and unknown type of properties … I am using it something like this –
    MultipleDynamicPropertiesAsGeneric show = new MultipleDynamicPropertiesAsGeneric();
    Cheers

  4. Manu Parashar says:

    Thats a good code snippet for unknown number of properties and unknown type of properties … I am using it something like this –
    MultipleDynamicPropertiesAsGeneric show = new MultipleDynamicPropertiesAsGeneric();

  5. Manu Parashar says:

    Its somehow deleting object, object ..

  6. Philip says:

    Is there a way to loop through all the properties/members of a class passed in – as in my question on StackOverflow?

    I have several web-services that need the SoapBody populated from a string array which is defined by an enumerated constant (the enum matches the members of the web-service class)

Leave a Reply