2011-02-18 51 views
4

在我的遊戲中,我有一個枚舉(約200個長)與不同的GameEntityType s。保存相關常量的最佳做法?

當遊戲被保存時,只有一個GameEntityType數組被寫入到保存文件中。

要重建遊戲世界,並顯示有關GameEntityTypes 的各種信息,我需要列出更多的額外細節(常量值)。 這意味着每個GameEntityType都有與其相關的其他值。 這些值經常在每一幀都被訪問。 我的目標是有一個簡單的方法來從GameEntityTypeID(枚舉)中獲取所有額外的信息。 例如,當我從保存文件中讀取0x1時,我可以簡單地訪問Name和所有其他 信息,這些信息與數組中的number/enum相似,如下所示:「Constants.TextureList [GameEntityType]」,將返回字符串"Stone_Texture.DDS"

實施例用於第一枚舉條目的附加/相關聯的信息:

類型: string,字符串Flag-Enum: "Visual-Classification"boolbool 值: "StoneBlock""Stone_Texture.DDS"0x0102falsetrue

我的第一個方法,這是創建一個靜態GameEntityTypeInfo類 有一個像每增加信息類型下列成員:

公共靜態常量字符串[] = {「StoneBlock」。 .. [more entrys]};

當然這是一個糟糕的解決方案,因爲我無法在任何地方添加GameEntityType的 而無需更新所有其他列表。 我還必須將邏輯單元分成數據類型單元(這是一個問題!因爲當我決定不再需要特定的EntityType時,我必須去超過6個列表!)

接下來,我試圖通過從這些數據集中取出一個結構並將它們添加到一個靜態數組來解決這個問題。 但創建一個列表與額外的信息,而構造函數(雖然遊戲開始) 似乎仍然不是最好的解決方案。

問題:如何創建一個快速(每幀至少使用5000次名稱/分類查找總數)並容易訪問(最好是索引器)這些常量值?

類似下面的查詢將是最好的 「Constants.TextureList [GameEntityType]」

+0

什麼是紋理列表?這與你的gameentitytypes有什麼關係? – Joe 2011-02-18 01:58:38

+0

這是一個列表,我可以查找實體使用的紋理。 另外還會有其他一些列表:EntityType暗示的每個附加值的一個列表(或數組)。 澄清問題: 想象一下,它完全像一個存儲所有不同實體類型和匹配值的「僅查找SQL表」,其中列爲: GameEntityType(uint);紋理(字符串);顏色(int [3])... 此數據表使我能夠僅保存實體類型(小保存文件),然後使用EntityType和查找的組合信息重新創建遊戲世界 – riki 2011-02-18 12:48:33

回答

2

通過繼承:

public abstract class Enumeration : IComparable 
{ 
private readonly int _value; 
private readonly string _displayName; 

protected Enumeration() 
{ 
} 

protected Enumeration(int value, string displayName) 
{ 
    _value = value; 
    _displayName = displayName; 
} 

public int Value 
{ 
    get { return _value; } 
} 

public string DisplayName 
{ 
    get { return _displayName; } 
} 

public override string ToString() 
{ 
    return DisplayName; 
} 

public static IEnumerable<T> GetAll<T>() where T : Enumeration, new() 
{ 
    var type = typeof(T); 
    var fields = type.GetFields(BindingFlags.Public | BindingFlags.Static | BindingFlags.DeclaredOnly); 

    foreach (var info in fields) 
    { 
     var instance = new T(); 
     var locatedValue = info.GetValue(instance) as T; 

     if (locatedValue != null) 
     { 
      yield return locatedValue; 
     } 
    } 
} 

public override bool Equals(object obj) 
{ 
    var otherValue = obj as Enumeration; 

    if (otherValue == null) 
    { 
     return false; 
    } 

    var typeMatches = GetType().Equals(obj.GetType()); 
    var valueMatches = _value.Equals(otherValue.Value); 

    return typeMatches && valueMatches; 
} 

public override int GetHashCode() 
{ 
    return _value.GetHashCode(); 
} 

public static int AbsoluteDifference(Enumeration firstValue, Enumeration secondValue) 
{ 
    var absoluteDifference = Math.Abs(firstValue.Value - secondValue.Value); 
    return absoluteDifference; 
} 

public static T FromValue<T>(int value) where T : Enumeration, new() 
{ 
    var matchingItem = parse<T, int>(value, "value", item => item.Value == value); 
    return matchingItem; 
} 

public static T FromDisplayName<T>(string displayName) where T : Enumeration, new() 
{ 
    var matchingItem = parse<T, string>(displayName, "display name", item => item.DisplayName == displayName); 
    return matchingItem; 
} 

private static T parse<T, K>(K value, string description, Func<T, bool> predicate) where T : Enumeration, new() 
{ 
    var matchingItem = GetAll<T>().FirstOrDefault(predicate); 

    if (matchingItem == null) 
    { 
     var message = string.Format("'{0}' is not a valid {1} in {2}", value, description, typeof(T)); 
     throw new ApplicationException(message); 
    } 

    return matchingItem; 
} 

public int CompareTo(object other) 
{ 
    return Value.CompareTo(((Enumeration)other).Value); 
} 
} 

這裏的文章:http://www.lostechies.com/blogs/jimmy_bogard/archive/2008/08/12/enumeration-classes.aspx

0

不知道如果我的理解到底是什麼你正在努力尋找,但是,如果你經過快速查找,它聽起來像你要找的是Dictionary<string, List<string>>