开发者

Using strings instead of enums?

开发者 https://www.devze.com 2023-02-04 17:56 出处:网络
Is it comm开发者_如何学Con place to use a string for comparison as opposed to an enum?I am aware about your context, but as a first step you can just refactor this way:

Is it comm开发者_如何学Con place to use a string for comparison as opposed to an enum?


I am aware about your context, but as a first step you can just refactor this way:

Step 1

if (typeOfObject == "UAV")
{
    DoSomeWork(_stkObjectRootToIsolateForUavs);
}
else if (typeOfObject == "Entity")
{
    DoSomeWork(_stkObjectRootToIsolateForEntities);
}

private void DoSomeWork(IAgStkObject agStkObject)
{
    IAgStkObject stkObject = agStkObject.CurrentScenario.Children[stkObjectName];
    IAgDataProviderGroup group = (IAgDataProviderGroup)stkUavObject.DataProviders["Heading"];
    IAgDataProvider provider = (IAgDataProvider)group.Group["Fixed"];
    IAgDrResult result = ((IAgDataPrvTimeVar)provider).ExecSingle(_stkObjectRootToIsolateForUavs.CurrentTime);

    stkObjectHeadingAndVelocity[0] = (double)result.DataSets[1].GetValues().GetValue(0);
    stkObjectHeadingAndVelocity[1] = (double)result.DataSets[4].GetValues().GetValue(0);
}

Then consider replasing if's with switch:

Step 2

switch (typeOfObject)
{
    case "UAV":
        DoSomeWork(_stkObjectRootToIsolateForUavs);
        break; 
    case "Entity":
        DoSomeWork(_stkObjectRootToIsolateForEntities);
        break;
    default:
        throw new NotImplementedException():
}

This can be even better when using enums.


At the very least, the strings should be declared as constants (or perhaps readonly fields) somewhere, instead of spread out through the code. However, this looks like the schoolbook example for when to use an enum.

public enum ObjectType
{
   UAV,
   Entity,
   // and so on
}


To add to @Restuta's answer, I'd use a

IDictionary<MyEnumifiedString, Action<IAgStkObject>> 

to get rid of that if.


I'd agree with @Frederik that this seems a perfect case for using enums, but it could be that the only thing you can get out of the application is a string. In which case your example is perfectly OK.

Oh yes - and make sure you have the string constants defined in one place, preferably a config file so that if they change the other application you don't have to recompile yours.


Regarding your first question I will always use a defined type to store the strings simply to have one location for change if needed.

So for your example i would have the following

public sealed class RootTypes
{
    public const string Entity = "entity";
    public const string UAV = "uav";
}

Your code then updates to this

    typeOfObject = typeOfObject.ToLower();
    if (typeOfObject == RootTypes.UAV)
    {
        stkUavObject = _stkObjectRootToIsolateForUavs.CurrentScenario.Children[stkObjectName];
        var group = (IAgDataProviderGroup) stkUavObject.DataProviders["Heading"];
        var provider = (IAgDataProvider) group.Group["Fixed"];
        IAgDrResult result = ((IAgDataPrvTimeVar) provider).ExecSingle(_stkObjectRootToIsolateForUavs.CurrentTime);
        stkObjectHeadingAndVelocity[0] = (double) result.DataSets[1].GetValues().GetValue(0);
        stkObjectHeadingAndVelocity[1] = (double) result.DataSets[4].GetValues().GetValue(0);
    }
    else if (typeOfObject == RootTypes.Entity)
    {
        IAgStkObject stkEntityObject = _stkObjectRootToIsolateForEntities.CurrentScenario.Children[stkObjectName];
        var group = (IAgDataProviderGroup) stkEntityObject.DataProviders["Heading"];
        var provider = (IAgDataProvider) group.Group["Fixed"];
        IAgDrResult result = ((IAgDataPrvTimeVar) provider).ExecSingle(_stkObjectRootToIsolateForEntities.CurrentTime);
        stkObjectHeadingAndVelocity[0] = (double) result.DataSets[1].GetValues().GetValue(0);
        stkObjectHeadingAndVelocity[1] = (double) result.DataSets[4].GetValues().GetValue(0);
    }

The issue of code redundancy has been anserwed by Restuta


Use enums with bit flags:

[Flags]
public enum MyFlags
{
    SomeFlag = 0x1, // 001
    OtherFlag = 0x2,// 010
    ThirdFlag = 0x4 // 100
}

var firstObject = MyFlags.SomeFlag;
var secondObject = MyFlags.SomeFlag | MyFlags.OtherFlag;

if(((int)secondObject & MyFlags.SomeFlag) != 0) 
{
    // true
}

if(((int)secondObject & MyFlags.OtherFlag) != 0) 
{
    // true
}

if(((int)firstObject & MyFlags.SomeFlag) != 0) 
{
    // true
}

if(((int)firstObject & MyFlags.OtherFlag) != 0) 
{
    // false
}

This article would be helpful.

0

精彩评论

暂无评论...
验证码 换一张
取 消