Страница 1 из 1

зачем компонентам присваивать переменные?

СообщениеДобавлено: 28 июн 2022, 20:57
pantsurevolution
Всем привет!
У меня вопрос академический, чтобы понимать, прямой практической значимости не имеет.

Что происходит, когда мы делаем вот так
targetManager = GameObject.Find("Target").GetComponent<Manager>();

1 Почему бы сразу не работать с компонентом, вместо того, чтобы присваивать его переменной? Для экономии вычислительных мощностей? Всегда ли мощности экономятся? Если тебе надо сделать одно действие с компонентом, то вроде бы ничего особо не экономится.
2 Работая с переменной, мы напрямую меняем объект, на который она ссылается, или все происходит более хитрым способом?
3 Вообще хотелось бы понять нужность таких вот переменных и алгоритм их работы.

спасибо

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 28 июн 2022, 21:12
Alkos26Rus
Если GetComponent используется более одного раза, то лучше через ссылку, да экономятся мощности, в твоем случае еще и GameObject.Find может быть очень медленным, когда на сцене куча объектов, поэтому лучше сразу при старте например дать ссылку и дальше уже работать с ней

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 30 июн 2022, 17:45
Jarico
pantsurevolution писал(а):Всем привет!
targetManager = GameObject.Find("Target").GetComponent<Manager>();


держи мой скриптик для создания статичного класса
https://gist.github.com/redheadgektor/0cd72ff9dcd8f4b8243a24bd2435d0e1

pantsurevolution писал(а):спасибо


Пожалуйста...

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 30 июн 2022, 18:27
Alkos26Rus
Jarico писал(а):держи мой скриптик для создания статичного класса
https://gist.github.com/redheadgektor/0cd72ff9dcd8f4b8243a24bd2435d0e1


Он ему не подойдет, потому как 100% его Manager имеет ссылки и настроенные поля, а твой скрипт создает новый объект и накидывает компонент с полями по умолчанию

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 01 июл 2022, 00:34
Jarico
Alkos26Rus писал(а):Он ему не подойдет, потому как 100% его Manager имеет ссылки и настроенные поля, а твой скрипт создает новый объект и накидывает компонент с полями по умолчанию

Можно бахнуть scriptable object в ассетах и подгружать его из ресурсов при запуске скрипта (абстрактный метод OnInitialized)... Все изменения будут сохраняться в ассетах и не нужно будет постоянно править значения

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 02 июл 2022, 13:29
pantsurevolution
Спасибо всем за ответы, я не все понял, потому что я тупой, но надеюсь, когда-нибудь пойму )

Вопрос был скорее в том, зачем мне вообще указывать Юнити дорогу к скрипту "Manager".
То есть, у нас есть класс Manager, но вместо того, чтобы сказать "Юнити, сделай Manager.Function()"

1 Мы создаём еще одну (лишнюю) переменную класса Manager, то есть Юнити может получить доступ к этому классу.
private Manager targetManager;

2 Указываем дорогу к самому скрипту, где описан класс Manager, как будто Юнити не может найти его.
GameObject.Find("Target").GetComponent<Manager>();

3 Присваиваем весь класс нашей переменной
targetManager = GameObject.Find("Target").GetComponent<Manager>();

4 Используем нужную функцию.
targetManager.Function();


Как бы процесс противоречит самому себе, и перегружен, с моей дилетантской точки зрения. Я не против концепции, что ПРОСТО ТАК НАДО ДЕЛАТЬ, но разве это не результат какой-то не очевидной (для меня) логики?

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 02 июл 2022, 22:10
Alkos26Rus
pantsurevolution писал(а):Вопрос был скорее в том, зачем мне вообще указывать Юнити дорогу к скрипту "Manager".
То есть, у нас есть класс Manager, но вместо того, чтобы сказать "Юнити, сделай Manager.Function()"

Ну скрипт Manager может висеть на нескольких объектах, у кого именно тебе нужно вызвать функцию юнити не знает, поэтому нужно указать ссылку, а что бы с любого места вызывать функцию без ссылок, это статичные функции нужны

pantsurevolution писал(а):2 Указываем дорогу к самому скрипту, где описан класс Manager, как будто Юнити не может найти его.
GameObject.Find("Target").GetComponent<Manager>();

GameObject.Find это поиск нужного объекта, естественно юнити не Ванга и не знает какой именно объект тебе нужен, а GetComponent<Manager>(); это уже обращение к компоненту этого объекта

почитай про scriptable object, может тебе это нужно

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 02 июл 2022, 22:45
1max1
Сам по себе метод Find тяжеловесный, вызвать его каждый раз невыгодно. Что если методов, которые нужно вызвать в Manager несколько? Что если эти методы вызываются в апдейте каждый кадр? Ну можешь сказать пока фпс, на мобилках уж точно.

Синтаксис:
Используется csharp
GameObject.Find("Target").GetComponent<Manager>().targetManager.Function_One();
GameObject.Find("Target").GetComponent<Manager>().targetManager.Function_Two();
GameObject.Find("Target").GetComponent<Manager>().targetManager.Function_Three();

Re: зачем компонентам присваивать переменные?

СообщениеДобавлено: 04 авг 2022, 07:13
MrDmitry
pantsurevolution писал(а):Спасибо всем за ответы, я не все понял, потому что я тупой, но надеюсь, когда-нибудь пойму )

Вопрос был скорее в том, зачем мне вообще указывать Юнити дорогу к скрипту "Manager".
То есть, у нас есть класс Manager, но вместо того, чтобы сказать "Юнити, сделай Manager.Function()"

1 Мы создаём еще одну (лишнюю) переменную класса Manager, то есть Юнити может получить доступ к этому классу.
private Manager targetManager;

2 Указываем дорогу к самому скрипту, где описан класс Manager, как будто Юнити не может найти его.
GameObject.Find("Target").GetComponent<Manager>();

3 Присваиваем весь класс нашей переменной
targetManager = GameObject.Find("Target").GetComponent<Manager>();

4 Используем нужную функцию.
targetManager.Function();


Как бы процесс противоречит самому себе, и перегружен, с моей дилетантской точки зрения. Я не против концепции, что ПРОСТО ТАК НАДО ДЕЛАТЬ, но разве это не результат какой-то не очевидной (для меня) логики?

Если я правильно понял ваш вопрос, то вам нужно подтянуть ваши знания принципов ООП и тогда возможно таких вопросов бы не возникало.

Скажем у вас есть объект Target на этих объектах есть класс Manager в котором скажем есть свойство hp
У каждого из этих объектов значение свойства hp не обязательно будет совпадать. А если мы захотим изменить одному из объектов target значения свойства hp на -5 а другому на +10, как мы это сделаем не имея прямой ссылки какому именно объекту менять hp? Описанный вами вариант(синтактически не верный) изменил бы hp всем объектам Target hp на одинаковое значение.