【问题标题】:Having an issue with C# and constructors."ItemType.ItemType(string) is inaccessible due to its protection level"C# 和构造函数存在问题。“ItemType.ItemType(string) 由于其保护级别而无法访问”
【发布时间】:2013-02-23 18:29:17
【问题描述】:

我正在为我的 Unity 游戏制作一个物品系统,我正在使用 C# 来完成它。我有一个名为 ItemType 的抽象类,它包含有关特定类型项目的信息(例如其名称、重量、市场价值、ID 等)。然后我必须从 ItemType 类继承的项目类、ItemSword 和 ItemCoin。我还有一个 ItemManager 类,它实例化 ItemCoin 和 ItemSword 并自动为我分配一个 ID。我的问题是我在尝试继承类时遇到构造函数错误。

ItemType 的构造函数采用一个参数,一个名为 name 的字符串。当我为 ItemCoin 做构造函数时,我确保它使用

调用基类
ItemCoin(string name): base(name){
//Stuff
}

就像this page 上所说的那样。

错误是说“名称”由于其保护级别而无法访问,就好像我已将其设为私有一样。不过,我不明白这是怎么可能的,因为我是不给它任何类型的访问修饰符,因为它是一个参数。 ItemSword 没有给我这个错误,但这可能是因为编译器仍然卡在 ItemCoin 上。

当我不给“base”任何参数时,它告诉我 ItemType 没有带有 0 个参数的构造函数。如果我根本不使用“base”,或者我不给它任何构造函数,也会发生同样的事情。

供参考,这是我的完整源代码。

ItemType.cs:

using UnityEngine;
using System.Collections;

public abstract class ItemType{

    public int itemID; //The id of this item
    public string itemName; //The text name of this item

    public int stackSize = 99; //The maximum amount of this item allowed in a stack.  Use -1 for infinite
    public int maxAllowedInOneContainer = -1; //The maximum amount of this item allowed in a single container.  Use -1 for infinite.
    public int weight = 0; //The weight of this item
    public int marketValue = 0; //The standard price of this item in stores

    ItemType(string name){

        itemName = name;

    }

}

ItemCoin.cs:

using UnityEngine;
using System.Collections;

public class ItemCoin : ItemType {

    ItemCoin(string name): base(name){

        stackSize = -1;

    }

}

ItemSword.cs:

using UnityEngine;
using System.Collections;

public class ItemSword : ItemType{

    ItemSword(string name): base(name){
        maxAllowedInOneContainer = 1;
        stackSize = 1;
    }

}

ItemManager.cs:

using UnityEngine;
using System.Collections;

public class ItemManager {

    public const int MAX_ITEMS = 3200;

    private static ItemType[] itemList = new ItemType[MAX_ITEMS];
    public static int numberOfItems = 0;

    ItemManager(){

        /*When you make a new item, add it to this huge list of item declarations, or else it won't do anything!*/
        ItemSword sword = addItem(new ItemSword("Sword")); //Adds the sword item
        ItemCoin coin = addItem(new ItemCoin("Coin"));
    }

    public ItemType addItem(ItemType item){

        //Add the item to the list
        itemList[numberOfItems] = item;

        //Tell the item its id number
        item.itemID = numberOfItems;

        //Increment the total number of items by one.  This will be the id of the next added item.
        numberOfItems += 1;

        return item;

    }

    public int findItemID(string name){
        //Finds the item id for an item with a given name

        bool found = false;

        for (int i = 0; i < numberOfItems; i++){

            if (itemList[i].itemName == name){
                found = true;
                return itemList[i].itemID;
                break;
            }

        }

        if (found == false){
            throw new ItemIDNotFoundException();
        }

    }

    public string findItemName(int id){

        if (id >= itemList.Length){
            throw new ItemIDNotFoundException();
        }
        else{
            return itemList[id].name;
        }

    }

    public ItemType GetItem(int id){
        //Returns a reference(pointer) to the item type with a given id.
        return itemList[id];
    }

}

【问题讨论】:

    标签: c# constructor


    【解决方案1】:

    在类中,private 是默认的可访问性级别,因此如果不指定它,您的构造函数就是私有的。

    【讨论】:

      【解决方案2】:

      当你有这样的构造函数时:

      ItemType(string name){
      
          itemName = name;
      
      }
      

      它是私有的,只能由类本身访问。当没有指定访问修饰符时,private 是类成员的默认值。为了能够从子类中使用它,您需要使其至少为protected

      protected ItemType(string name)
      {
          itemName = name;
      }
      

      或者您可以将其设为publicinternal。由于这是一个抽象类,从其他类本身或子类中访问它是没有意义的,protected 可能是最合适的选择。

      【讨论】:

      • 同意。在abstract 类中,拥有public(或protected internal)实例构造函数是毫无意义的。但如果他愿意,他可以 成为internal。但是,protected 对于抽象类的实例构造函数来说是最自然(也是限制最少)的访问级别。
      【解决方案3】:

      在类中,默认的可访问性级别是private。如果你不指定它,那么你的构造函数将是private

      来自MSDN

      请注意,如果你没有在构造函数中使用访问修饰符,它 默认情况下仍将是私有的。但是,private 修饰符通常显式使用 以明确该类不能被实例化。

      【讨论】:

        猜你喜欢
        • 2013-06-04
        • 2017-09-22
        • 2011-07-16
        • 2015-09-26
        • 2011-09-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多