简体   繁体   English

如何获取存储在数组中的类中的值?

[英]How do I get a value within a class stored within an array?

I'm making a C# script in Unity.我正在 Unity 中制作 C# 脚本。 My intention is to create a class Scenario , create classes representing different scenarios, which would then be stored in an array scenarioListAll .我的目的是创建一个类Scenario ,创建代表不同场景的类,然后将这些类存储在一个数组scenarioListAll

A (simplified) version of the code is as follows:代码的(简化)版本如下:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class OverallManager2 : MonoBehaviour
{

public static object[] scenarioListAll = new object[40];

public class Scenario
{
    public string scenarioDesc;
    public bool surprise;     // The 'surprise' bool I want to reference is defined here
    public string surpriseType;
    public int[] leftOption;
    public int[] rightOption;
    public int scenarioNumber;

    public Scenario(string st, bool sp, int[] l, int[] r, int n)
    {
        scenarioDesc = st;
        surprise = sp;
        leftOption = l;
        rightOption = r;
        scenarioNumber = n;
    }

    // I haven't used this, but I'm not sure if this matters so I'm including this too
    public Scenario(string st, bool sp, string spt, int[] l, int[] r, int n)
    {
        scenarioDesc = st;
        surprise = sp;
        surpriseType = spt;
        leftOption = l;
        rightOption = r;
        scenarioNumber = n;
    }
}


public static int[] getArray(int a, int b, int c, int d, int e, int f)
{
    int[] arr = new int[6] {a, b, c, d, e, f};
    return arr;
}


// Storing scenarios, am looking for the bool (2nd position)
public Scenario s1 = new Scenario("Test1", false, getArray(1, 1, 1, 1, 1, 1), getArray(1, 1, 1, 1, 1, 1), 1);
public Scenario s2 = new Scenario("Test2", true, getArray(1, 1, 1, 1, 1, 1), getArray(1, 1, 1, 1, 1, 1), 2);
public Scenario s3 = new Scenario("Test3", false, getArray(1, 1, 1, 1, 1, 1), getArray(1, 1, 1, 1, 1, 1), 3);

    void Awake()
    {
        // Store scenarios in object array
        scenarioListAll[0] = s1;
        scenarioListAll[1] = s2;
        scenarioListAll[2] = s3;

        for(int i = 0; i < 40; i++)
        {
            object temp = scenarioListAll[i];     // Trying to extract the object stored in the array in a temp object
            bool surpriseCheck = temp.surprise;     // I am having problems with this line
            if(surpriseCheck == true)
            {
                // Do something
            }
        }
    }
// Ignoring start and update since they're irrelevant in this context
}

What I would like to do is to check whether the surprise element within a newly defined scenario (eg s1 ) is true.我想做的是检查新定义的场景(例如s1 )中的surprise元素是否为真。 To do that, I was planning to extract the scenario stored in the array scenarioListAll , and then extract the surprise component from there.为此,我计划提取存储在数组scenarioListAll中的scenarioListAll ,然后从那里提取surprise组件。 However, I'm couldn't figure out how to do this (eg in the code shown above, it returns Compiler Error CS1061).但是,我无法弄清楚如何执行此操作(例如,在上面显示的代码中,它返回编译器错误 CS1061)。

I don't think I was able to find any documentation on this either, but I might not have understood something.我认为我也无法找到任何关于此的文档,但我可能没有理解某些内容。 I'm learning on my own so please bear with my poor knowledge/presentation.我正在自己学习,所以请忍受我的知识/介绍不足。

Thank you for your time.感谢您的时间。 Your help is much appreciated.非常感谢您的帮助。

You are having a compilation issue due to the fact that the c# compiler doesn't know that temp is a Scenario since you declared it as "object".由于 c# 编译器不知道 temp 是一个场景,因为您将其声明为“对象”,因此您遇到了编译问题。 If you want to loop through the scenarios and check to see if they are a surprise you can use something like this:如果您想遍历场景并检查它们是否令人惊讶,您可以使用以下内容:

 foreach(Scenario temp in scenarioListAll)
 {
        bool surpriseCheck = temp.surprise;     
        if(surpriseCheck == true)
        {
            // Do something
        }
 }

Another way of accomplishing the same task with more control over the iteration would be:通过对迭代的更多控制来完成相同任务的另一种方法是:

 for(int i = 0; i < scenarioListAll.Length; i++)
 {
        Scenario temp = scenarioListAll[i];
        bool surpriseCheck = temp.surprise;     
        if(surpriseCheck == true)
        {
            // Do something
        }
 }

The benefit of the first version is that you don't have to worry about overrunning the bounds of the array.第一个版本的好处是您不必担心超出数组的边界。 As Mike added below you could also use var to have the compiler fill in the type for you.正如 Mike 在下面添加的那样,您还可以使用 var 让编译器为您填写类型。

It's sometimes easiest to allow the compiler to determine the type of a variable for us.有时让编译器为我们确定变量的类型是最简单的。

In your case, you've specified that the variable temp will be of type object .在您的情况下,您已指定变量temp的类型为object Now, that's fine, but while a Scenario derives from object , and object is the lowest level class in the .Net environment, and is not a Scenario .现在,这很好,但是虽然Scenario派生自object ,而 object 是 .Net 环境中的最低级别类,而不是Scenario

The var keyword doesn't mean that the declared type is of a "variable" type, instead it's telling the compiler just to "fill in" the correct type, based on the action you're taking. var关键字并不意味着声明的类型是“变量”类型,而是告诉编译器根据您正在采取的操作“填写”正确的类型。 So, to put this in to action in your case, you could do this instead:因此,要在您的情况下将其付诸实践,您可以这样做:

    for( var i = 0; i < 40; i++ )                   // notice the use of var here as well
    {
        var scenario = scenarioListAll[i];          // renamed temp to scenario
        // var surpriseCheck = scenario .surprise;  // var used but line not required
        if( scenario.surprise )
        {
            // Do something
        }
    }

I went overboard there to demonstrate that the compiler is quite happy with the var keyword just about wherever you'd specify a data type as a type for a variable.我在那里过分说明了编译器对var关键字非常满意,几乎在您将数据类型指定为变量类型的任何地方。 Obviously not when you're trying to cast types, and there ARE sometimes where you'd want to specify the exact type you're trying to instantiate.显然不是当您尝试强制转换类型时,有时您想要指定您尝试实例化的确切类型。

In your case, your next issue will be that you've defined the array as having 40 object elements, but you've then only instantiated 3 Scenario elements (which is valid, but probably not quite what you want overall).在您的情况下,您的下一个问题将是您已将数组定义为具有 40 个object元素,但您随后仅实例化了 3 个Scenario元素(这是有效的,但可能不是您想要的整体)。 So your code, as it stands, is going to NullReference error out.因此,就目前而言,您的代码将出现 NullReference 错误。 You'll be able to avoid that, with a small modification, so your amended code could look like this, to include some type checks:只需稍加修改,您就可以避免这种情况,因此您修改后的代码可能如下所示,以包含一些类型检查:

for( var i = 0; i < scenarioListAll.Length; i++ )
{
    // First, check to see if the object in the array cell is a Scenario.
    // If the item in the cell is a Scenario, check to see if surprise is set.
    if ( scenarioListAll[i] is Scenario scenario && scenario.surprise )
    {
        // Do something
    }
}

for more information on the is keyword, check the Microsoft Docs here .有关is关键字的详细信息,请在此处查看Microsoft Docs

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM