遍历列表以检查boolean在ScriptableObject中是否为真

时间:2019-04-04 15:38:32

标签: c# visual-studio unity3d

我有一个字符可写对象'Character',并且有一个布尔IsMale。我也有一个“团队”可编写脚本的对象,它具有来自“角色可编写脚本”对象类的字符列表。现在,我想在Team Class中创建一个自定义方法,以循环浏览此列表,并检查有多少个男性角色,而没有几个。

Character.cs

 using UnityEngine;

 // Personal Attributes
 public string firstName;
 public string middleName;
 public string lastName;
 public string fullName;

 public bool isMale;

Team.cs

 using UnityEngine;

 public List<Character> characters;

 // For adding ten players.
 public void AddPlayer(Character p1, p2, p3, p4, p5, p6, p7, p8, p9, p10)
 {
 characters.Add(p1);
 characters.Add(p2);
 characters.Add(p3);
 characters.Add(p4);
 characters.Add(p5);
 characters.Add(p6);
 characters.Add(p7);
 characters.Add(p8);
 characters.Add(p9);
 characters.Add(p10);
 }
 // I want to loop through these ten characters in the list and tell how many are males and how many are not

同样,我想在Team Class中创建一个自定义方法来循环浏览此列表,并检查有多少个男性角色,有几个不是男性。

有关@derHugo评论中的问题 Character.cs

using UnityEngine;
using System;

[CreateAssetMenu()]
public class Character : ScriptableObject
{
    // Personal Attributes
    public string firstName;
    public string middleName;
    public string lastName;
    public string fullName;

    public bool isMale;

    private int age;
    public int personalMoney;

    public Sprite image;

    // Game Attributes
    public int totalRuns;
    public int salary;

    public enum characterTypes { PlayerCharacter, Manager, Player, Staff };
    public characterTypes characterType;
    public enum battingHands { LeftHanded, RightHanded };
    public battingHands battingHand;
    public enum bowlingHands { LeftHanded, RightHanded };
    public bowlingHands bowlingHand;
    public enum battingMentalities { Aggressive, Balanced, Defensive };
    public battingMentalities battingMentality;
    public enum bowlingMentalities { Aggressive, Balanced, Defensive };
    public bowlingMentalities bowlingMentality;

    // Skills
    // Technical Skills
    public int technical; // Overall Technical
    public int judgement; // Batting
    public int agility; // Running, Low means if player accidentaly falls down, the time he will take to get back up
    public int cardioFitness; // Injury
    public int muscleFitness; // Injury and Hitting Power
    public int runSpeed; // Running
    public int strength; // Hitting Power

    // Methods
    // Personal Attributes Methods
    public void CalculateAge(DateTime dateOfBirth)
    {
        age = 0;
        age = DateTime.Now.Year - dateOfBirth.Year;
        if (DateTime.Now.DayOfYear < dateOfBirth.DayOfYear)
            age = age - 1;
    }

    // Starting Game Methods Required
    public void SetCharacterType(characterTypes cT)
    {
        Debug.Log("Setting Character Type for " + fullName);

        cT = characterType;

        if (cT == characterTypes.PlayerCharacter)
        {
            Debug.Log(fullName + " is a Player Character");
        }
        else if (cT == characterTypes.Manager)
        {
            Debug.Log(fullName + " is a Manager");
        }
        else if (cT == characterTypes.Player)
        {
            Debug.Log(fullName + " is a Player");
        }
        else if (cT == characterTypes.Staff)
        {
            Debug.Log(fullName + " is a Staff");
        }
        else
        {
            Debug.Log("No Character Type");
        }
    }
    public void TechnicalAverage()
    {
        technical = (judgement + agility + cardioFitness + muscleFitness + runSpeed + strength / 600) * 100;
    }
}

1 个答案:

答案 0 :(得分:1)

您可以例如为此使用Linq Count(我宁愿在这里使用属性,但也可以使用课程方法来做同样的事情。):

using System.Linq;

public int Males
{
    get
    {
        return characters != null ? characters.Count(c => c.isMale) : 0;
    }
}

public int Females
{
    get
    {
        return characters != null ? characters.Count(c => !c.isMale) : 0;
    }
}

您只需使用该值即可,例如

Debug.LogFormat(this, "Males: {0}, Females: {1}", Males, Females);

提示:即使Unity Inspector自动初始化List和数组字段,您也应该始终将其与类似的定义一起使用

public List<Character> characters = new List<Character>(10);

只是为了确保在调用null时它永远不会Add,并确保将默认容量设置为您希望列表稍后拥有的计数。

或者您可以使用

Character[] characters = new Character[10];

因为您始终不希望尺寸是动态的。 (注意,但是Unity中的Inspector始终会覆盖这些定义)

更好的原因:List在后​​台始终将其值存储在数组中。通过使用Add添加元素,它每次都会检查数组是否仍然足够大,如果不足够,则将其扩展为双倍大小(请参见here

public void AddPlayer(Character p1, p2, p3, p4, p5, p6, p7, p8, p9, p10)
{
    characters.Add(p1); // characters has now capacity 4
    characters.Add(p2);
    characters.Add(p3);
    characters.Add(p4);
    characters.Add(p5); // characters reallocated and has now capacity 8 
    characters.Add(p6);
    characters.Add(p7);
    characters.Add(p8);
    characters.Add(p9); // characters reallocated and has now capacity 16
    characters.Add(p10);
}

因此您看到使用Add 10或11次总是分配比实际需要更多的内存。

我会

// hide because if you do it via the method you probably don't
// want to add items via Inspector which would get overwritten later anyway
[HideInInspector] public Character[] characters = new Character[10];

public void AddPlayer(Character p1, p2, p3, p4, p5, p6, p7, p8, p9, p10)
{
    characters[0] = p1;
    characters[1] = p2;
    characters[2] = p3;
    characters[3] = p4;
    characters[4] = p5;
    characters[5] = p6;
    characters[6] = p7;
    characters[7] = p8;
    characters[8] = p9;
    characters[9] = p10;
}

除此之外,访问或更改数组或列表中的值的方式没有太大区别。


要设置每个字符所需的所有值,您可以/应该使用适当的构造函数(不过我会更改命名):

[Serializable]
public class Character
{
    // Personal Attributes
    public string firstName;
    public string middleName;
    public string lastName;
    public string fullName;

    public bool isMale;

    public Character(string _firstName, string _middleName, string _lastName, bool _isMale)
    {
        firstName = _firstName;
        middleName = _middleName;
        lastName = _lastName;

        fullName = string.Format("{0} {1} {2}", firstName, middleName, lastName);

        isMale = _isMale;
    }
}