Я строю игру, в которой есть много разных видов животных и множество популяций разных видов. В этой упрощенной версии каждый вид определяется только его доминированием, размером и набором потребностей. Моя цель - уметь легко создавать новые виды с помощью инспектора Unity, и я делал это с помощью объектов сценариев:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Species : ScriptableObject
{
[SerializeField] private List<Need> needs = default;
[Range(0.0f, 10.0f)]
[SerializeField] private float dominance = default;
[Range(0.0f, 10.0f)]
[SerializeField] private float size = default;
// ... etc
public float Dominance => dominance;
public float Size => size;
public float GetNeedSeverity(NeedType needType)
{
foreach (Need need in needs)
{
if (need.Type == needType)
{
return need.Severity;
}
}
throw new System.ArgumentException($"Species does not have need {needType}");
}
}
Это позволяет мне использовать инспектор для простого проектирования новых виды до времени выполнения. Тем не менее, должны быть «экземпляры» этого вида во время выполнения, которые являются популяциями. Чтобы сделать это, я создал класс популяции, в котором хранится ссылка на его вид:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Population : MonoBehaviour
{
private Species species = default;
public float Dominance => species.Dominance;
public float Size => species.Size;
}
Способ, которым она реализована сейчас, состоит в том, что вместо того, чтобы класс популяции имел идентичные поля для вида и просто копировал все По данным из класса видов, класс популяции просто ссылается на класс видов и вместо этого извлекает из него информацию.
Является ли это правильным подходом?
Кажется, у обоих подходов есть проблемы. Если я скопирую все данные из класса видов в каждый класс популяции, во время выполнения будет много дублирующих данных и много, казалось бы, дублированного кода. Однако, когда я просто ссылаюсь на класс видов из класса популяции, а не копирую его данные, тогда мне также приходится выполнять множество функций в классе популяции, чтобы получить конкретные данные из класса видов. Кроме того, есть список потребностей, которые есть у каждого вида, и если какой-то другой класс должен собрать данные о конкретной потребности населения в c, функция будет неприятной. Ни один из подходов не кажется очень чистым.
Класс потребности:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public enum NeedType { Grass, Water, Pinecone } // and many more
public class Need : ScriptableObject
{
[SerializeField] private NeedType type = default;
[SerializeField] private float severity = default;
public NeedType Type => type;
public float Severity => severity;
// ... etc
}
Один из этих способов лучше? Или есть лучший способ настроить классы?
Спасибо за любую помощь!