Dlaczego Akka jest dobra na współbieżność?

9

Jestem nowy w Akka i środowisku aktorskim - jestem pewien, że brakuje mi czegoś oczywistego, proszę z góry przeprosić.

Wciąż czytam, że jednym z głównych punktów wyboru Akka jest sposób zarządzania współbieżnością.

Nie jest dla mnie jasne, dlaczego Akka jest taka wyjątkowa; Rozumiem, że jest wielu małych aktorów, którzy są bardzo lekcy i szybcy; jak to jednak może mi pomóc, gdy dwóch użytkowników jednocześnie zapisuje formularz?

Czy nadal nie potrzebuję jakiegoś rodzaju blokady współbieżności (pesymistycznej / optymistycznej / itp.)?

abx78
źródło
Zastanawiasz się, dlaczego aktorzy są dobrzy do współbieżności, a konkretnie Akka?
scriptin
Wouldn't I still need some sort of concurrency lock (pessimistic/optimistic/etc..)?- Tak, ale to odpowiedzialność leży u podstaw RDBMS, a nie aktora. Bardzo prawdopodobne, że aktor Akka nie rozmawia bezpośrednio z użytkownikiem. Raczej aktor Akka i użytkownik (zasadniczo inny aktor) bezpośrednio wchodzą w interakcję z bazą danych.
Robert Harvey,

Odpowiedzi:

7

Jedną z zalet modeli przetwarzania komunikatów, takich jak aktorzy i agenci, jest to, że tradycyjne problemy z współbieżnością (przede wszystkim synchronizacja stanu współdzielonego) nie stanowią już problemu. Aktor może zachować stan prywatny i dowolnie go aktualizować bez blokad. Struktura aktora zapewnia przetwarzanie tylko jednej wiadomości na raz. Dzięki przetwarzaniu serializowanemu kod może być zapisywany bez blokady.

W przykładzie użytkowników zapisujących formularz, zakładając, że aktor przechowuje listę niektórych danych z każdego formularza, aktor może aktualizować listę bez blokad, ponieważ struktura gwarantuje, że przetwarzany będzie tylko jeden formularz naraz. Tradycyjnie musiałbyś blokować dostęp do listy lub korzystać z równoległej listy.

Strategia współbieżności jest nieco inną sprawą i nadal spoczywa na tobie odpowiedzialność (żadna strategia nie jest najczęstszą strategią). Aby nieznacznie zmienić przykład, powiedzmy, że obaj użytkownicy próbują jednocześnie zaktualizować instancję formularza SAME. Bez strategii współbieżności zmiany jednej osoby zastąpią drugą (prawdopodobnie ostatnia wygrywa). W porządku, ale w najlepszym wypadku powoduje to nieoczekiwane zachowanie użytkownika, którego zmiany zostały zastąpione. Jeśli zobaczą właśnie zmieniony formularz, będzie on miał nieoczekiwane wartości (od drugiego użytkownika). W najgorszym przypadku (gdy nie mówimy tylko o aktualizacjach formularzy, ale o rzeczach takich jak wysyłanie zamówień), może to spowodować różnego rodzaju straty (czas, przychody itp.).

Korzystanie ze strategii współbieżności pomaga zidentyfikować te przypadki i być w stanie je rozwiązać na podstawie reguł biznesowych. Na przykład optymistyczna współbieżność każe użytkownikowi przesłać wersję formularza, który aktualizuje. Gdy aktor przystępuje do przetworzenia zmiany, zauważa, że ​​drugi użytkownik myśli, że aktualizuje wersję 5, gdy formularz faktycznie ma wersję 6 z powodu aktualizacji pierwszego użytkownika. Teraz przynajmniej możemy powiadomić drugiego użytkownika, że ​​formularz już się zmienił, odkąd zaczął go edytować. Lub jakiekolwiek zasady, które firma chce tam egzekwować.

W przypadku aktualizacji formularza prawdopodobnie nie przejmujesz się tak bardzo współbieżnością (jak sądzę, zależy). Ale w innych przypadkach może być bardzo ważne, aby przynajmniej móc sprawdzać i obsługiwać naruszenia. Możesz nawet zignorować naruszenie współbieżności, na przykład jeśli użytkownicy zmienili różne sekcje (aby kontynuować analogię formularza). Lub jeśli zmiana ma duży wpływ na biznes (duże zamówienie), chcesz ją zaakceptować i rozwiązać drobne konflikty później (np. Coroczna aktualizacja informacji kontaktowych nie została zakończona).

Wierzę, że Akka ma wiele innych wymiarów, takich jak sposób radzenia sobie z awariami, nadzorcami itp., Które są ważnymi rozważaniami dla deweloperów.

Kasey Speakman
źródło
9

Zamierzam pisać ogólnie o modelu aktora (nie tylko Akka) w porównaniu z innymi modelami współbieżności, takimi jak klasyczna współbieżność oparta na blokadzie i czysta pamięć transakcyjna.

Zalety

  1. Łatwiejsza koncepcja do zrozumienia i użycia

    • Współbieżność na podstawie blokady jest trudna; w szczególności bardzo trudno jest to zrobić poprawnie, ponieważ istnieje wiele pojęć, które należy zrozumieć i zastosować, aby być poprawnym i wydajnym: zamki, semafory, wątki, synchronizacja, wzajemne wykluczanie, bariera pamięci itp.

    • Z drugiej strony aktorzy są koncepcją bardziej abstrakcyjną; masz aktorów, którzy wysyłają i odbierają wiadomości. Nie trzeba chwytać i używać pojęć niskiego poziomu, takich jak bariera pamięci.

  2. Wymusza niezmienność

    • Zmienność jest źródłem wielu błędów i błędów w programowaniu, szczególnie w aplikacjach wielowątkowych. Model aktora rozwiązuje ten problem, wymuszając niezmienność.
  3. Mniej podatny na błędy

    • Z powyższych dwóch powodów
  4. Wydajny

    • Nie tak wydajna jak dobra, napisana blokada, ale ogólnie bardziej wydajna niż programowa pamięć transakcyjna.
  5. Łatwo skalowalny

    • Przynajmniej teoretycznie aplikacja powinna skalować się całkiem dobrze, dodając więcej aktorów do wykonywania zadań. Z blokadą jest dość trudno skalować.

Niedogodności

  1. Nie wszystkie języki łatwo wymuszają niezmienność;

    • Erlang, język, który jako pierwszy spopularyzował aktorów, ma niezmienność u podstaw, ale Java i Scala (właściwie JVM) nie wymuszają niezmienności.
  2. Wciąż dość skomplikowane

    • Aktorzy opierają się na asynchronicznym modelu programowania, który nie jest tak prosty i łatwy do modelowania we wszystkich scenariuszach; szczególnie trudne jest obsługiwanie scenariuszy błędów i awarii.
  3. Nie zapobiega impasowi ani głodowi

    • Dwaj aktorzy mogą znajdować się w stanie, który czeka jeden od drugiego; w ten sposób masz zakleszczenie, podobnie jak w przypadku blokad, chociaż znacznie łatwiej jest je debugować. Pamięć transakcyjna gwarantuje jednak brak impasu.
  4. Nie tak wydajne

    • Z powodu wymuszonej niezmienności i ponieważ wielu aktorów musi się przełączyć, używając tego samego wątku, aktorzy nie będą tak wydajni jak współbieżność oparta na blokadzie.

Wniosek

Współbieżność oparta na blokadach jest najbardziej wydajna, ale jest trudna do zaprogramowania i podatna na błędy; programowa pamięć transakcyjna jest najbardziej przejrzysta, łatwa do zaprogramowania i podatna na błędy, ale jest również najmniej wydajna. Aktorzy są gdzieś pomiędzy tymi dwoma modelami ze wszystkimi aspektami: łatwość programowania, wydajność i podatność na błędy.

m3th0dman
źródło
Czy dla twojej przewagi numer 2 nie powinno to brzmieć: „ Zmienność jest źródłem wielu błędów ...” i „… rozwiązuje ten problem, zabraniając zmienności ” zamiast „ niezmienności ”? Drugie zdanie zawiera również dwa zbędne wzmianki o rozwiązaniu problemu.
8bittree
@ 8bittree Tak, masz rację; błędnie napisałem. Na wypadek, gdybyś nie wiedział, możesz edytować odpowiedzi, aby rozwiązać takie problemy.
m3th0dman
Wiem o tym, po prostu niechętnie wprowadzam zmiany, które odwracają lub drastycznie zmieniają znaczenie czegoś, na wypadek, gdyby to było nieporozumienie z mojej strony.
8bittree,
Czy potrafisz rozwinąć impas? Wygląda na to, że musiałbyś zbudować bardzo niezręczną konfigurację aktorów (dwukierunkowa komunikacja), aby się z tym spotkać. Jeśli używasz wzorca zapytań (A prosi B o odpowiedź, B przetwarza żądanie i odpowiada na nadawcę żądania, ale nigdy nie kontaktuje się bezpośrednio z A) Nie widzę, jak możliwy jest impas
Daenyth,
1
@ Daenyth Zgadzam się, że musiałbyś użyć dziwnej konstrukcji, aby osiągnąć impas z aktorami; ale z podobnej perspektywy musiałbyś użyć dziwnej konstrukcji, aby osiągnąć impas dzięki współbieżności opartej na blokadzie (chociaż zgadzam się, że łatwiej jest stworzyć impas z mutexem niż z aktorem). W każdym razie chodzi o to, że tylko pamięć transakcyjna gwarantuje, że nie będziesz mieć impasu bez względu na to, jaką dziwną konstrukcję wybrałeś.
m3th0dman