枚举值设置为不同的数字/重置枚举值

时间:2011-09-11 10:56:26

标签: c# enums numbers int

我正在尝试创建一个程序,根据您提供的起始音符计算不同的音阶。

我有一个不同笔记的枚举:

public enum NoteValue
{
    A = 0,
    Asharp = 1,
    B = 2,
    C = 3,
    Csharp = 4,
    D = 5,
    Dsharp = 6,
    E = 7,
    F = 8,
    Fsharp = 9,
    G = 10,
    Gsharp = 11
}

然后我有一个设置每个音符的方法

        public void setNotes(NoteValue startingNote)
        {
        //Creates an array of notes the size that is specified
        theNote = new Note[(numberOfNotes)];

        //Sets the notes
        theNote[0] = new Note(startingNote);
        theNote[1] = new Note((startingNote + step[1]));
        theNote[2] = new Note((startingNote + step[2] + step[1]));
        theNote[3] = new Note((startingNote + step[3] + step[2] + step[1]));
        theNote[4] = new Note((startingNote + step[4] + step[3] + step[2] + step[1]));
        theNote[5] = new Note((startingNote + step[5] + step[4] + step[3] + step[2] + step[1]));
        theNote[6] = new Note((startingNote - step[7]));

        Console.WriteLine("{0} \n{1} \n{2} \n{3} \n{4} \n{5} \n{6}",
            theNote[0].value, theNote[1].value, theNote[2].value, theNote[3].value,
            theNote[4].value, theNote[5].value, theNote[6].value);
    }

我遇到的问题是如果它发生了我从G开始(在我的枚举中是10), 它只会在G#之后开始打印数字。我可以做到这样它会回来 11之后回到0,而不是继续下去?

我会得到类似的东西(大规模):

而不是

有什么方法可以解决这个问题吗?谢谢。

2 个答案:

答案 0 :(得分:4)

在C#中定义的枚举基本上是整数类型(整数)的“强类型”包装。

如果你想要整数的这种包装行为,常见的解决方案是使用模(%)运算符:

int note = 12;
var correctlyWrappedNote = note % 12; // will equal 0

这在逻辑上相当于在除以12后取余数。

然后,您应该将其转换回NoteValue类型:

var actualNote = (NoteValue)correctlyWrappedNote;

如果您将负数输入模数,则会得到否定结果。如果你必须处理负数,那么还有一个额外的步骤:

int note = -1;
var correctlyWrappedNote = note % 12; // will equal -1

if (correctlyWrappedNote < 0)
    correctlyWrappedNote = 12 + correctlyWrappedNote; // will equal 11

var actualNote = (NoteValue)correctlyWrappedNote; // Will equal Gsharp

答案 1 :(得分:2)

@Merlyn的答案包含了你需要做的事情的要点,但仅仅因为你的枚举成员恰好是12并且因为每个数字0到11分配给其中一个枚举成员而使用%12是一个食谱对于破碎的代码。为了使其更具弹性,你可以像这样写

var notes = Enum.GetValues(typeof(NoteValue)); //array
var startingNote = Array.IndexOf(notes,NoteValue.Fsharp);//8
var fourNotesAfterStartingNote = notes[(startingNote+4)%notes.Length];//Asharp

即使添加了新注释,上述代码也将继续正常运行。不太可能 - 但是代码总是会改变:)