Wielowątkowość w Visual Scripting

0

Witam.
Czy może wie ktoś jak zrobić "taski" w Unity w Visual Scripting?
Powoli rozwijam swoją grę i będę potrzebował wykonywania zadań złożonych w odrębnym wątki.
Nie chodzi mi o coroutine.

0

A próbowałeś i jest jakiś problem? Czy nie patrzyłeś jeszcze?
Przyznam, że sam nie miałem okazji, ale jakbym miał robić to:

  • jeśli chodzi o samo wykonanie czegoś, nie widzę problemu, robisz custom bloczek, który Ci odpala wątek
  • jeśli chodzi o zwracanie, może być ciut ciężej, ale zawsze możesz zrobić odpalanie wątku, a w bloczkach oczekiwanie w coroutine na wynik
0
Boski napisał(a):

A próbowałeś i jest jakiś problem? Czy nie patrzyłeś jeszcze?
Przyznam, że sam nie miałem okazji, ale jakbym miał robić to:

  • jeśli chodzi o samo wykonanie czegoś, nie widzę problemu, robisz custom bloczek, który Ci odpala wątek
  • jeśli chodzi o zwracanie, może być ciut ciężej, ale zawsze możesz zrobić odpalanie wątku, a w bloczkach oczekiwanie w coroutine na wynik

Próbowałem na Coroutine i przy 100.000 pętli blokowało się na kilka sekund. Próbowałem coś kombinować z "Create Async Operation", ale także bezskutecznie.
A o co dokładnie chodzi z odpalaniem w bloczku? Chodzi o wykonywanie w State Machiine czy jak?
PS:
Zrobiłem dla przykładu prosty szablon: Jeśli nacisnę spację to dodaj do tablicy 100.000 liczb pseudolosowych z przedziału od 0 do
10000.
Dodaje zrzut jak wygląda Flow
Zrzut ekranu (10).png

0

blokowało w sensie freeze?

chodzi mi o to, że możesz zrobić sobie własny bloczek / metodę do visual scripting, i tam w środku użyć wątków
https://docs.unity3d.com/Packages/com.unity.visualscripting@1.7/manual/vs-create-custom-node.html

ale btw:
ważne jest, w którym momencie robisz yield w coroutine. Jeśli co jedną liczbę, to nie powinno blokować, ale będzie długo trwać. ile liczb generować optymalnie z jednym przebiegiem? to już musisz sprawdzić, pewnie 100-1000 będzie okej

i jeszcze:
najbardziej newralgiczne miejsca generalnie warto wyciągać do kodu, i wtedy zawołać z poziomu visual scripting. na pewno będzie wydajniej

0

Częściowo odciążyłem kod dodając Wait For Next Frame (wcześniej nie miałem tego), jednak dalej to nie rozwiązuje kłopotu mojego...
Rozumiem że muszę napisać kod w C# według tego zalecenia? link
Nie ma "ładniejszego" sposobu pisania tak jak normalnie w C#?
Zapytałem się Chat GPT i polecił wykorzystanie w jakiś sposób Job System, tylko nie wiem jak ;/

0

A możesz napisać co konkretnie robisz, że jest to takie ciężkie?
Jakie są te złożone zadania?

0

A w jakim miejscu wstawiłeś? Masz tam pętle, żeby generować te liczby partiami, po 100 czy 1000?
Po jednym takim przebiegu wait, i powinno być okej.
Co do tego linka co wstawiłeś - on jest chyba do starszej wersji bloczków, zobacz w linku co podesłałem, jak tam się wstawia nowe bloczki - wygląda imo sporo czytelniej
edit: chociaż chyba nie, tak samo jest, zmyliła mnie końcówka z portami

0

Ogólnie to pisząc grę chcę mieć interakcję z większą ilością obiektów i dlatego chciałem część zadać przełożyć na osobne wątki.
Dlatego dla przykładu zrobiłem większą tablicę, która miała symulować obciążenie.
Poza tym chciałem zobaczyć jaki jest sposób w Visual Scripting na tworzenie skryptów w nowych wątkach.

0

Nie przyszło Ci do głowy, że może robisz coś w niewłaściwy sposób i mógłbyś to zrealizować tak, żeby osobne wątki nie były konieczne?

1

Jest taka opcja, ale chcę zobaczyć jak można rozłożyć zadania w Visual Scripting na inne wątki.
I chyba znalazłem rozwiązanie. Poza tym co zasugerował Boski z własnym blokiem to chyba znalazłem prostszy sposób.
Po prostu odwołam si do wykonania akcji w kodzie C#.

Edit:
Ok, znalazłem częściowe rozwiązanie.

  1. Tworzymy plik C#
  2. Dodajemy go do Typów w Visual Scripting (VS)
  3. Regenerujemy projekt
  4. Piszemy normalnie metody tak jak chcemy, ponieważ VS automatycznie je doda.
  5. Efektem takiego pisania jest obrazek poniżej
    Kod aby takie coś wyszło:
public class Test : MonoBehaviour
{
    public void TestJob(ref List<int> intList)
    {

    }
}

Taki dość ważny PS-ik; ;)
Wykonałem ten sam skrypt w następujących scenariuszach i jakie mam wyniki jeśli chodzi o czas wykonania?
Wykonałem wpisanie wartości od 0 1.000.000 do listy (Listy<int>) przy użyciu pętli for.

  1. w Visual Scripting czas wykonania miałem: 13s.
  2. W przypadku wykonania tego samego skryptu w wątku głównym w C# czas wynosił: 0,0086793 s
    Przy wykonaniu tego ale zamiast do 1.000.000 zwiększyłem do 100.000.000 czas ten wyniósł: od 0,9 do 1,3s

3.Przy wykorzystaniu wątku dodatkowego czas ten wyniósł: od 0,01 do 0,3 (ale nie blokowało wątku głównego)
Po zwiększeniu czas ten wyniósł: od 1 do 1,3s (ale nie blokowało wątku głównego)

Działania na wątku robiłem z wykorzystaniem Async, Await i Task
Przy wykorzystaniu Thread czas ten zmniejszył się i dla wartości:
1.000.000 wyniósł od 0,09 do 0,012
100.000.000 wyniósł od 1,02 do 1,3

Co ciekawe po dodaniu 500.000.000 elementów do tablicy przy kolejnych 100.000.000 pokazało komunikat
"OutOfMemoryException: Out of memory"

Warto zaznaczyć że o tyle fajne jest użycie Listy, że nie trzeba przepisywać zmiennych po zakończeniu pracy wątku, ponieważ Lista przechowuje adres w którym się zaczyna.
Wychodzi na to że jak oneracje na większych ilościach plików to lepiej dodać do Visual Scripting wstawkę w C#.
Dobre zastosowanie przy respawnie surowców czy na SI przeciwników w RTS-ach

1 użytkowników online, w tym zalogowanych: 0, gości: 1