C# RPG库存:添加和删除项目

C# RPG库存:添加和删除项目,c#,game-engine,C#,Game Engine,到目前为止,我有: class Inventory { private Potion[] potions; private Weapon[] weapons; private Armor[] armor; private Food[] food; private Ore[] ores; public int InventorySlots {get;set;} public Inventory() {

到目前为止,我有:

class Inventory {
     private Potion[] potions;
     private Weapon[] weapons;
     private Armor[]  armor;
     private Food[]   food;
     private Ore[] ores;

     public int InventorySlots {get;set;}
     public Inventory() {
            InventorySlots = 10;
            BuildInventory();
     }
     public Inventory(int slots) {
            InventorySlots = slots;
            BuildInventory();
     }
     public void BuildInventory() {
            potions = new Potion[InventorySlots];
            weapons = new Weapons[InventorySlots];
            armor = new Armor[InventorySlots];
            food = new Food[InventorySlots];
            ores = new Ore[InventorySlots]
     }
}

例如,Itf,我想在10个插槽的库存中添加一件新武器,我该如何添加和删除它?

看起来您无法将武器设置在库存类之外,因为它是私有的,但是如果你是在Inventory类中进行的,因为它是一个数组,你只需将武器分配给武器数组的索引。要删除它,只需将该武器索引设置为null

weapons[index] = weapon;  // add
weapons[index] = null;  // remove
在数组位置使用对象之前,请确保并检查空值:

if (potions[4] != null)
{
    potions[4].DrinkMe();
}
您可以通过重新分配null来删除项

请注意,所有数组位置都将以null开头。守则:

potions = new Potion[InventorySlots];

分配一个
药剂
数组,但不在每个数组插槽中放置新的
药剂
实例。这取决于你自己。

我个人会将这些公开

private Potion[] potions;
private Weapon[] weapons;
private Armor[]  armor;
private Food[]   food;
private Ore[] ores;
但是,如果您想让它们保持私有,那么就创建方法来访问不同数组的不同位置

例如

public Weapon getWeaponAtPositon(int index)
{
    if (index > 0 && index < InventorySlots)
        return weapons[index];
    else
        return null;
}

public void setWeaponAtPositon(Weapon weapon, int index)
{
    if (weapon != null && index > 0 && index < InventorySlots)
        weapons[index] = weapon;
}

public void deleteWeaponAtPositon(int index)
{
    if (index > 0 && index < InventorySlots)
        weapons[index] = null;
}
公共武器获取武器位置(int索引)
{
如果(索引>0&&index<库存插槽)
归还武器[索引];
其他的
返回null;
}
公共无效设置武器位置(武器,智力指数)
{
如果(武器!=null&&index>0&&index0&&index<库存插槽)
武器[索引]=空;
}
您可以为您拥有的不同数组重复这些操作,这样您一次只能访问一个字段,从而提供了从类外修改数组的更安全的方法(即使仍然很容易,也不太可能弄乱数组)


希望能有所帮助。

为了显著简化问题,您可以创建一个基类“Item”,您所有的Item类型都是从该基类派生而来的:

public class Item
{
    // put any common attributes here
}

public class Armor : Item
{
    // define properties for Armor here
}

public class Weapon : Item
{
    // define properties for weapons here
}
当您创建这样的子类时,您可以使用
变量来存储任何派生类。您可以创建一个新的
武器
实例,并将其分配给例如
物资
类型的库存槽。因此,您的
Inventory
类成为
Item
s的集合

假设您希望数组与库存位置的1:1映射,并且不希望事情自行重新安排,那么使用数组方法可能是一个不错的选择

class Inventory
{
    // Array to store items
    public Item[] Items { get; private set; }

    // Inventory capacity is array length
    public int Capacity { get { return (Items == null) ? 0 : Items.Length; } }

    // Constructor
    public Inventory(int capacity = 10)
    {
        SetInventorySize(capacity);
    }

    // Set size of inventory, retaining contents where possible
    public void SetInventorySize(int cap)
    {
        if (cap <= 0)
            Items = null;
        else if (Items == null)
            Items = new int[cap];
        else
            Array.Resize(ref Items, cap);
    }

    // Get index number of first free slot in inventory
    public int FirstAvail()
    {
        if (Items != null)
        {
            for (int i = 0; i < Items.Length; ++i)
            {
                if (Items[i] == null)
                    return i;
            }
        }
        return -1;
    }

    // Add item to array, returning index or -1 on failure
    public int AddItem(Item item)
    {
        if (Items != null)
        {
            for (int i = 0; i < Items.Length; ++i)
            {
                if (Items[i] == null)
                {
                    Items[i] = item;
                    return i;
                }
            }
        }
        return -1;
    }
}
as
操作将检查对象的真实类型,如果不匹配,则返回null。因此,如果您将
药剂
物品存储在库存的0号槽中,它将不会尝试将其用作
护甲
武器
物品


当然,这是一个人为的例子。在
类中定义基本的公共操作并在子类中重写它们会更有用。然后,您只需调用(例如)
item.DefaultAction()
,并为每个子类型覆盖
DefaultAction
的实现,以执行适当的操作。

就个人而言,我会使用列表而不是数组-
私有列表
,然后您可以使用
武器添加。添加(weaponInfo)
如果项目数是固定的,那么使用数组并不是不合理的。@EricJ。这取决于管理数组中的项需要做多少工作,以及是否值得。
List
类方法简化了许多数组处理,并为操作提供了方便的助记符名称。@user2097371您确定每个项需要10个插槽吗?这似乎与你的不匹配。当我说10个插槽清单时,我的意思是有10个项目插槽,武器将占据其中一个。
class Inventory
{
    // Array to store items
    public Item[] Items { get; private set; }

    // Inventory capacity is array length
    public int Capacity { get { return (Items == null) ? 0 : Items.Length; } }

    // Constructor
    public Inventory(int capacity = 10)
    {
        SetInventorySize(capacity);
    }

    // Set size of inventory, retaining contents where possible
    public void SetInventorySize(int cap)
    {
        if (cap <= 0)
            Items = null;
        else if (Items == null)
            Items = new int[cap];
        else
            Array.Resize(ref Items, cap);
    }

    // Get index number of first free slot in inventory
    public int FirstAvail()
    {
        if (Items != null)
        {
            for (int i = 0; i < Items.Length; ++i)
            {
                if (Items[i] == null)
                    return i;
            }
        }
        return -1;
    }

    // Add item to array, returning index or -1 on failure
    public int AddItem(Item item)
    {
        if (Items != null)
        {
            for (int i = 0; i < Items.Length; ++i)
            {
                if (Items[i] == null)
                {
                    Items[i] = item;
                    return i;
                }
            }
        }
        return -1;
    }
}
// get the first item in the inventory
Item item = inventory.Items[0];

if ((Armor armorItem = item as Armor) != null)
{
    // Code to execute for Armor items
    armorItem.Wear();
}
else if ((Weapon weaponItem = item as Weapon) != null)
{
    // Code to execute for Weapon items
    weaponItem.Equip();    
}
else if ((Potion potionItem = item as Potion) != null)
{
    // Code to execute for Potion items
    potionItem.Drink();
}