Fórum Root.cz
Hlavní témata => Vývoj => Téma založeno: Serverfreak 25. 05. 2017, 10:06:56
-
Může mi někdo prosím poradit, jakým způsobem přepsat server? Kontext: mám webovou službu, rozhraní je přes JSON, server je napsaný v Javě (přímo nad standardní knihovnou, žádný framework), kód je malý (nějaké základní zpracování dat, IPC k jedné lokální komponentě a přístup do databáze), ale požadavků není málo (tisíce za minutu) a současná verze je dost náročná na paměť a občas se zasekává (asi GC). Koukal jsem na node.js, ale jednovláknovost se mi moc nepozdává (server má ARM64 s 16 vlákny). Mám na přepsání čas a chuť experimentovat, jen si nejsem jistý, jakým směrem se vydat (mám prototyp v čistém C nad syscally, ale nedal bych ruku do ohně za spolehlivost, je to jen proof of concept).
-
go, erlang, haskell
lightweight procesy, komunikace mezi nimi, a v případě haskellu STM a typový systém (a aeson)
-
Začněte tím, že zjistíte, co způsobuje ty problémy. A pak tu danou věc buď opravte (pokud je to chyba), nebo vymyslete jiný způsob řešení (pokud je to věc návrhu). Pokud jenom současnou aplikaci přepíšete do jiného jazyka, skončíte (v lepším případě) s aplikací, která bude mít úplně ten samý problém.
Pokud to chcete přepisovat, můžete použít např. Spring (http://projects.spring.io/spring-framework/) (a Spring Boot (http://projects.spring.io/spring-boot/)), kde už máte podporu pro webové služby, JSON i přístup k databázím, IPC záleží na implementaci. Nebudete se pak muset věnovat infrastruktuře aplikace a budete se moci soustředit na její jádro. Případně, pokud byste chtěl optimalizovat síťovou vrstvu, doporučuju použít framework Netty (http://netty.io/), který je postavený nad NIO a odstíní vás od komplikací síťové komunikace.
To, že to máte napsané přímo nad standardní knihovnou a nepoužíváte žádný framework ani knihovny, je podle mne největší slabina, protože pak se vysilujete na řešení něčeho, co už dávno před vámi vyřešil někdo jiný (a nejspíš lépe).
Pokud si jenom chcete vyzkoušet přepsat to do něčeho jiného a je vám jedno, do čeho, zaměřil bych se na jazyky, které míří tímhle směrem, jak napsal „v“, do výčtu bych přidal třeba ještě Rust. Node.js na to podle mne není vhodný, ten je vhodný pro prototypování nebo izomorfní aplikace, ale není orientován na výkon pod zátěží. V čistém C bych to nepsal – to byste se opět vysiloval nad něčím, co je už dávno vyřešené. A než to řešit nějakým frameworkem v C, spíš bych zvolil jiný jazyk, protože tím získáte podporu nejen ze strany knihovny, ale i ze strany jazyka a překladače.
-
Jste si jistý, že úzkým hrdlem je aplikace? Většinou bývá problém v databázi. Tisíce požadavků za minutu je nic.
Nejdřív bych se podíval na konfiguraci databáze.
Pokud je problém v aplikaci:
Jestli ty požadavky většinu času čekají na odpověď té lokální komponenty nebo databáze, zkusil bych navýšit počet souběžně zpracovávaných požadavků. V nejhorším případě můžete zkusit použít nějaký neblokující framework. Na jazyku nezáleží.
Další možnost je realizovat pomalá čekání v nějakém task queue a výsledek posílat klientovi pomocí websocketu. Nemusíte přepisovat celou aplikaci, stačí jen dlouho čekající části přesunout do task queue.
Přepsání celé aplikace bývá nejhorší možné řešení. Zrychlení se dá většinou docílit malou úpravou stávající aplikace.
Kdybyste chtěl přesto použít nodejs. Horizontální škálování nodejs http aplikací s nginx je triviální.
-
go, erlang, haskell
lightweight procesy, komunikace mezi nimi, a v případě haskellu STM a typový systém (a aeson)
To je nejspíš overkill. S největší pravděpodobností je jeho problém řešitelný nějakým malým fixem. Na jeho místě bych se snažil zachovat maximální množství stávajícího kódu.
-
go, erlang, haskell
lightweight procesy, komunikace mezi nimi, a v případě haskellu STM a typový systém (a aeson)
To je nejspíš overkill. S největší pravděpodobností je jeho problém řešitelný nějakým malým fixem. Na jeho místě bych se snažil zachovat maximální množství stávajícího kódu.
já jsem vycházel z toho "Mám na přepsání čas a chuť " :)
-
Začněte tím, že zjistíte, co způsobuje ty problémy. A pak tu danou věc buď opravte (pokud je to chyba), nebo vymyslete jiný způsob řešení (pokud je to věc návrhu). Pokud jenom současnou aplikaci přepíšete do jiného jazyka, skončíte (v lepším případě) s aplikací, která bude mít úplně ten samý problém.
Pokud to chcete přepisovat, můžete použít např. Spring (http://projects.spring.io/spring-framework/) (a Spring Boot (http://projects.spring.io/spring-boot/)), kde už máte podporu pro webové služby, JSON i přístup k databázím, IPC záleží na implementaci. Nebudete se pak muset věnovat infrastruktuře aplikace a budete se moci soustředit na její jádro. Případně, pokud byste chtěl optimalizovat síťovou vrstvu, doporučuju použít framework Netty (http://netty.io/), který je postavený nad NIO a odstíní vás od komplikací síťové komunikace.
To, že to máte napsané přímo nad standardní knihovnou a nepoužíváte žádný framework ani knihovny, je podle mne největší slabina, protože pak se vysilujete na řešení něčeho, co už dávno před vámi vyřešil někdo jiný (a nejspíš lépe).
Pokud si jenom chcete vyzkoušet přepsat to do něčeho jiného a je vám jedno, do čeho, zaměřil bych se na jazyky, které míří tímhle směrem, jak napsal „v“, do výčtu bych přidal třeba ještě Rust. Node.js na to podle mne není vhodný, ten je vhodný pro prototypování nebo izomorfní aplikace, ale není orientován na výkon pod zátěží. V čistém C bych to nepsal – to byste se opět vysiloval nad něčím, co je už dávno vyřešené. A než to řešit nějakým frameworkem v C, spíš bych zvolil jiný jazyk, protože tím získáte podporu nejen ze strany knihovny, ale i ze strany jazyka a překladače.
Děkuji. Prvotní "chyba" je v návrhu, protože každý požadavek se řeší v samostatném vlákně, ale stejně bych čekal, že GC si s tím poradí lépe. Jinak problém asi taky může být, že implementace SSL nad ARM je relativně pomalá.
To přepsání do C bylo jen cvičení, původně jsem chtěl libevent, ale nemá dobré reference. Myšlenka v pozadí je opustit Javu, nemyslím, že tady přináší nějaké výhody. Dík za tip na Rust, to vypadá hodně dobře, určitě s tím budu experimentovat.
-
go, erlang, haskell
lightweight procesy, komunikace mezi nimi, a v případě haskellu STM a typový systém (a aeson)
To je nejspíš overkill. S největší pravděpodobností je jeho problém řešitelný nějakým malým fixem. Na jeho místě bych se snažil zachovat maximální množství stávajícího kódu.
já jsem vycházel z toho "Mám na přepsání čas a chuť " :)
Ano, chci experimentovat :) Dík za tipy, Haskell je na mě v tomto případě trochu moc FP, ale na Go se určitě podívám (a porovná s tím Rustem).
-
go, erlang, haskell
lightweight procesy, komunikace mezi nimi, a v případě haskellu STM a typový systém (a aeson)
To je nejspíš overkill. S největší pravděpodobností je jeho problém řešitelný nějakým malým fixem. Na jeho místě bych se snažil zachovat maximální množství stávajícího kódu.
já jsem vycházel z toho "Mám na přepsání čas a chuť " :)
Ano, chci experimentovat :) Dík za tipy, Haskell je na mě v tomto případě trochu moc FP, ale na Go se určitě podívám (a porovná s tím Rustem).
o Rustu toho moc nevím, ale nevypadá, že by měl lightweight procesy (třeba mě někdo opraví), to by pro mě byl velký nedostatek
-
Souhlasím, že nejdříve je potřeba zjistit příčiny stávajících problémů a až dle toho se rozhodnout, co s tím. Příklad - záseky všech odpovědí mohou místo GC způsobovat třeba zámky v DB v kombinaci s nějakým delším/neoptimálním dotazem. Nebo něco úplně jiného, to ukáže jen analýza.
-
Prvotní "chyba" je v návrhu, protože každý požadavek se řeší v samostatném vlákně
To by vyřešilo použití běžného serveru nebo frameworku, které mají pool vláken, která zpracovávají spojení. Případně, pokud zpracování tráví hodně času nějakým čekáním, můžete využít asynchronní zpracování – nativně s Netty, podporu pro to má i Spring.
ale stejně bych čekal, že GC si s tím poradí lépe
Jste si jistý, že to souvisí s GC? Nebylo by pak řešením použít jiný GC?
Jinak problém asi taky může být, že implementace SSL nad ARM je relativně pomalá.
To je to, co jsem psal na začátku – nejprve zjistit, v čem je problém. Jestli je to velké množství vláken, GC nebo pomalé SSL jsou diametrálně odlišné věci.
Myšlenka v pozadí je opustit Javu, nemyslím, že tady přináší nějaké výhody.
Taky nepřináší žádné nevýhody. A výhodou je podle mne velké množství knihoven a frameworků, které můžete jenom vzít a použít – a můžete se soustředit na to, co je specifické pro vaši aplikaci.
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
tak zrovna erlang by takto pomohl, nebo go, nebo haskell
-
Prvotní "chyba" je v návrhu, protože každý požadavek se řeší v samostatném vlákně
Typická chyba Javistů...
Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
+1
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
tak zrovna erlang by takto pomohl, nebo go, nebo haskell
Erlang řeší problém velkého množství čekajících vláken. Pokud každé vlákno zpracovává například velké množství dat, tak Erlang ničemu nepomůže. Naopak to bude pomalejší.
-
Jestli všechny požadavky přistupují ke stejné databázi, tak s největší pravděpodobností nestíhá databáze.
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
Pokud je hlavní problém v tom, že se pro každý req spouští samostatné vlákno (a zároveň se OP chce zbavit Javy), tak by Erlang rozhodně pomohl. Dál v něm může každý req zpracovávat ve vlastním procesu a přitom se mu to krásně bude samo škálovat přes všechna dostupná jádra - žádný pool tam není potřeba, bude to fungovat samo, zabezpečí to erlangovský scheduler.
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
Pokud je hlavní problém v tom, že se pro každý req spouští samostatné vlákno (a zároveň se OP chce zbavit Javy), tak by Erlang rozhodně pomohl. Dál v něm může každý req zpracovávat ve vlastním procesu a přitom se mu to krásně bude samo škálovat přes všechna dostupná jádra - žádný pool tam není potřeba, bude to fungovat samo, zabezpečí to erlangovský scheduler.
Pokud ty procesy přistupují k nějakým omezeným prostředkům, nebo žerou hodně paměti, tak jich chcete mít jen omezený počet.
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
tak by Erlang rozhodně pomohl
Podstatné bylo to „pokud ta vlákna skutečně něco dělají“. Pokud je ten server přetížený tím, že má moc práce, nepomůže to, že budete práci jiným způsobem přerozdělovat. Tam je řešením jedině řadit požadavky do fronty a nepřijímat další požadavky, pokud je fronta moc dlouhá.
Přerozdělení pomůže jedině tehdy pokud ta vlákna ve skutečnosti nic moc nedělají a většinu času tráví čekáním. Pak může pomoci koncepce procesů použitá v Erlangu, a nebo třeba asynchronní zpracování v Javě – když se vlákno dostane do bodu, kde má na něco čekat, vlákno se uvolní a začne zpracovávat něco jiného. A teprve když je ten požadavek, který způsobil čekání, vyřízen, nějaké vlákno dostane ke zpracování odpověď.
-
Pokud ty procesy přistupují k nějakým omezeným prostředkům, nebo žerou hodně paměti, tak jich chcete mít jen omezený počet.
Ano - a přesně proto, pokud se týče CPU, spouští Erlangovský scheduler tolik OS-vláken, kolik je jader :) Není to závislé na počtu (erlangovských) procesů.
Pokud je problém s pamětí nebo GC, tak ten u Erlangu taky s velkou pravděpodobností nebude, protože v Erlangu je GC lehčí než v Javě.
Pokud je problém s DB, tak se i v Erlangu musí použít pool, tam nijak nepomůže.
Jedině pokud by aplikace dělala nějaké intenzivní výpočty, tak by byl Erlang vyloženě nevhodná volba.
Podstatné bylo to „pokud ta vlákna skutečně něco dělají“. Pokud je ten server přetížený tím, že má moc práce,
...tak nepomůže nic než optimalizovat kód nebo povýšit hw, protože Java je slušně výkonná a přepsáním do jiného jazyka se moc nezíská.
nepomůže to, že budete práci jiným způsobem přerozdělovat. Tam je řešením jedině řadit požadavky do fronty [...]
Netvrdil jsem, že pomůže přerozdělení, ale že v Erlangu člověk může dál psát tím pohodlným způsobem, že každý request řeší v samostatném "vláknu" (erlangovském procesu) a scheduler za něj rozprostření po dostupných CPU vyřeší (pro dobře napsaný kód velmi optimálně) sám. Čili má člověk optimalitu poolu zadarmo, aniž by nějaký pool, fronty, zamykání atd. musel řešit.
-
Čili má člověk optimalitu poolu zadarmo, aniž by nějaký pool, fronty, zamykání atd. musel řešit.
To samé platí i při použití vhodných frameworků nebo knihoven.
-
Pokud máte čas na trochu experimentování, neváhal bych zkusit Elixir + http://www.phoenixframework.org/
-
Pokud ty procesy přistupují k nějakým omezeným prostředkům, nebo žerou hodně paměti, tak jich chcete mít jen omezený počet.
Ano - a přesně proto, pokud se týče CPU, spouští Erlangovský scheduler tolik OS-vláken, kolik je jader :) Není to závislé na počtu (erlangovských) procesů.
Pokud je problém s pamětí nebo GC, tak ten u Erlangu taky s velkou pravděpodobností nebude, protože v Erlangu je GC lehčí než v Javě.
Pokud je problém s DB, tak se i v Erlangu musí použít pool, tam nijak nepomůže.
Jedině pokud by aplikace dělala nějaké intenzivní výpočty, tak by byl Erlang vyloženě nevhodná volba.
Procesy mohou pracovat s velkou datovou strukturou, přistupovat k jedné databázi, provádět operace na disku a podobně. Pokud každý Erlangovský proces načte do paměti několika-megabyteový soubor, tak vám dojde paměť úplně stejně jako v Javě.
Erlangovské procesy se opravdu hodí jen k udržování socketového spojení, kdy většinu času nic nedělají. Pro náročnější operace potřebujete frontu a omezení počtu souběžných operací.
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
Pokud je hlavní problém v tom, že se pro každý req spouští samostatné vlákno (a zároveň se OP chce zbavit Javy), tak by Erlang rozhodně pomohl. Dál v něm může každý req zpracovávat ve vlastním procesu a přitom se mu to krásně bude samo škálovat přes všechna dostupná jádra - žádný pool tam není potřeba, bude to fungovat samo, zabezpečí to erlangovský scheduler.
Jak řeší Erlang zásobníky, když udělám třeba milion procesů?
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
Pokud je hlavní problém v tom, že se pro každý req spouští samostatné vlákno (a zároveň se OP chce zbavit Javy), tak by Erlang rozhodně pomohl. Dál v něm může každý req zpracovávat ve vlastním procesu a přitom se mu to krásně bude samo škálovat přes všechna dostupná jádra - žádný pool tam není potřeba, bude to fungovat samo, zabezpečí to erlangovský scheduler.
Jak řeší Erlang zásobníky, když udělám třeba milion procesů?
http://erlang.org/doc/efficiency_guide/processes.html
-
Jestli ta vlákna skutečně něco dělají, tak Erlang ani Node.js nepomohou. Výpočetně náročné úlohy musíte zpracovávat v nějakém poolu s omezeným počtem vláken.
Pokud je hlavní problém v tom, že se pro každý req spouští samostatné vlákno (a zároveň se OP chce zbavit Javy), tak by Erlang rozhodně pomohl. Dál v něm může každý req zpracovávat ve vlastním procesu a přitom se mu to krásně bude samo škálovat přes všechna dostupná jádra - žádný pool tam není potřeba, bude to fungovat samo, zabezpečí to erlangovský scheduler.
Jak řeší Erlang zásobníky, když udělám třeba milion procesů?
http://erlang.org/doc/efficiency_guide/processes.html
Zajímavé, dík.
-
Malo info o tom kde to drhne .... ale co treba SSLOfload/Loadbalancing ? Proc to hned prepisovat ?
-
To samé platí i při použití vhodných frameworků nebo knihoven.
Jo, může být. Akorát frameworky a knihovny (obzvlášť "enterprise" v Javě) vždycky hrozí dalším bobtnáním a hromadou balastu, kterou člověk nevyužije...
Pokud každý Erlangovský proces načte do paměti několika-megabyteový soubor, tak vám dojde paměť úplně stejně jako v Javě.
Tak samozřejmě. Pokud mám 50 req/s a pro každý musím načíst několik MB, tak se můžu dostat do úzkých. Ale to nemá žádné řešení. Pool ani fronta to nijak nevyřeší, maximálně můžou trochu vyhladit špičky.
Erlangovské procesy se opravdu hodí jen k udržování socketového spojení, kdy většinu času nic nedělají. Pro náročnější operace potřebujete frontu a omezení počtu souběžných operací.
A čím se jako principielně ta fronta od těch erlangovských procesů liší?! Tím, že můžu stanovit horní limit počtu obsloužených requestů? To většinou pochopitelně nikdo nechce.
Jo, je rozdíl mezi rychlým jazykem (C,C++,Java,Rust apod) a pomalým Erlangem, ale nevidím rozdíl mezi procesy a frontami (kromě toho, že fronty musím pracně obhospodařovávat).
-
Erlangovské procesy se opravdu hodí jen k udržování socketového spojení, kdy většinu času nic nedělají. Pro náročnější operace potřebujete frontu a omezení počtu souběžných operací.
A čím se jako principielně ta fronta od těch erlangovských procesů liší?! Tím, že můžu stanovit horní limit počtu obsloužených requestů? To většinou pochopitelně nikdo nechce.
Jo, je rozdíl mezi rychlým jazykem (C,C++,Java,Rust apod) a pomalým Erlangem, ale nevidím rozdíl mezi procesy a frontami (kromě toho, že fronty musím pracně obhospodařovávat).
Rozdíl je v paměťové náročnosti. Výhoda je i v oddělení náročných úloh od ostatních. Nic obsluhovat nemusíte. Použijete hotové řešení.
Fronty úloh se používají i v Erlangu/Elixiru
https://github.com/akira/exq
-
Jo, může být. Akorát frameworky a knihovny (obzvlášť "enterprise" v Javě) vždycky hrozí dalším bobtnáním a hromadou balastu, kterou člověk nevyužije...
To ale platí skoro o všech knihovnách a nástrojích – i s Erlangem nebo i s glibc dostanete spoustu balastu, který váš program nevyužije. Ale vadí to něčemu? Tohle budete řešit maximálně u mikrokontrolerů s omezenou pamětí, a to je evidentně jiný typ úloh, než jaký se tu řeší.
Tím, že můžu stanovit horní limit počtu obsloužených requestů? To většinou pochopitelně nikdo nechce.
Chce a fronty to právě řeší. Pokud zvládnete zpracovat 1 požadavek za sekundu, můžete začít zpracovávat první požadavek, dalších třeba 5 může čekat ve frontě a další přicházející požadavky můžete odmítat. Tím zajistíte, že se bude zpracovávat aspoň ten 1 požadavek za sekundu, a když se jich náhodou sejde o něco víc, tak si chvíli počkají, ale nakonec se to tím tempem 1 požadavek/s zpracuje. Což je pořád podstatně lepší situace, než když přijmete 50 požadavků, veškeré zdroje vyčerpáte jenom na jejich příjem a už vám nezbydou zdroje na zpracování ani jediného požadavku.
Rozdíl je v paměťové náročnosti.
„Procesy“ v Erlangu jsou velmi lehké, nejsou to skutečné procesy OS – nemyslím, že by byly paměťově nějak náročné.
-
Rozdíl je v paměťové náročnosti.
„Procesy“ v Erlangu jsou velmi lehké, nejsou to skutečné procesy OS – nemyslím, že by byly paměťově nějak náročné.
Nemyslel jsem režii, ale paměť spotřebovanou pro řešení samotné úlohy.
-
ale stejně bych čekal, že GC si s tím poradí lépe
Jste si jistý, že to souvisí s GC? Nebylo by pak řešením použít jiný GC?
Pokud v nějakém jazyce musím explicitně vybírat GC, aby mi program fungoval, tak je něco hodně špatně.
-
[...] scheduler za něj rozprostření po dostupných CPU vyřeší (pro dobře napsaný kód velmi optimálně) sám. Čili má člověk optimalitu poolu zadarmo, aniž by nějaký pool, fronty, zamykání atd. musel řešit.
To nebude ipso facto schedulerem, ale tím, že tam je kooperativní rozvrhování. Stejně optimálně by to fungovalo v jakémkoliv jazyce nebo prostředí od Go přes GCD po - blahé paměti - WebObjects.
-
Rozdíl je v paměťové náročnosti.
Jak už tady zaznělo, jeden Erlangovský proces zabírá řádově 300 slov. Kde je jaká paměťová náročnost?!
Výhoda je i v oddělení náročných úloh od ostatních.
Což samozřejmě můžu (a měl bych) udělat i u procesů.
Fronty úloh se používají i v Erlangu/Elixiru
Ano - tam, kde k tomu je explicitní důvod. Což je docela málo kdy, protože právě co se v jiných prostředích řeší frontami, dá se často v Erlangu řešit procesy.
To ale platí skoro o všech knihovnách a nástrojích – i s Erlangem nebo i s glibc dostanete spoustu balastu, který váš program nevyužije.
Ano, ale tu funkcionalitu, o které se bavíme, mám v Erlangu přímo v runtimu.
Ale vadí to něčemu? Tohle budete řešit maximálně u mikrokontrolerů s omezenou pamětí, a to je evidentně jiný typ úloh, než jaký se tu řeší.
Vadí to v případě, že ten balast se například musí natahovat při startu, že v něm bývají chyby, že je to děsivý moloch, který nikdo neví, jak funguje atd. atd.
Chce a fronty to právě řeší.
Lidi nechtějí požadavky zahazovat. Lidi chtějí mít tak výkonné systémy, aby dokázaly všechny požadavky zpracovat - a mít i nějakou rezervu, popř. autoscaling. Zahazování by měla být nejzazší krizová možnost, není to něco, čím by kdokoli chtěl řešit problém.
To nebude ipso facto schedulerem, ale tím, že tam je kooperativní rozvrhování. Stejně optimálně by to fungovalo v jakémkoliv jazyce nebo prostředí od Go přes GCD po - blahé paměti - WebObjects.
Jasně, já jsem jenom chtěl říct, že v Erlangu typicky bývá hodně malých procesů a ty pak scheduler rozhazuje po dostupných vláknech. Hodně malých procesů má větší pravděpodobnost vlákna vytížit rovnoměrně, čistě statisticky. V jazycích, kde mám obvykle procesů míň, to nebude tak dobře fungovat (ale v principu je to to samý, o to se nehádám).
-
Pokud v nějakém jazyce musím explicitně vybírat GC, aby mi program fungoval, tak je něco hodně špatně.
Nevím o jazyku, u kterého byste explicitně vybíral GC. Já jsem psal o JVM, což je běhové prostředí. Také vůbec nebyla řeč o tom, že by program nefungoval. Jenom bylo zmíněno podezření (v diskusi ničím nepodložené), že by GC mohl ovlivňovat výkon aplikace – pak je logické prozkoumat charakteristiku použitého GC a porovnat ji s charakteristikami jiných dostupných GC a případně GC změnit. Na tom, že je v jednom běhovém prostředí dostupných více implementací GC, není nic špatného – každý se chová trochu jinak a hodí se tak pro jiný typ úloh. Například Linux má několik implementací plánovačů procesů, několik implementací plánovačů IO, několik implementací souborových systémů – obecně je to považováno za plus, protože si každý může vybrat, co zrovna on potřebuje, a není odkázán na jedno one size fits all řešení, které bude ve všech případech stejně špatné.
-
Rozdíl je v paměťové náročnosti.
Jak už tady zaznělo, jeden Erlangovský proces zabíra 309 slov. Kde je jaká paměťová náročnost?!
Ten proces pracuje s nějakými daty. Ta mohou být velká.
-
Ano, ale tu funkcionalitu, o které se bavíme, mám v Erlangu přímo v runtimu.
Pořád nevidím ten rozdíl. Když na to máte funkcionalitu přímo v runtime Erlangu, tak nevadí, že v tom runtime máte také spoustu funkcionalit, které nepoužijete. Ale když tu funkcionalitu máte v knihovně, tak to najednou vadí, že je v té knihovně i něco, co vůbec nepoužijete.
Vadí to v případě, že ten balast se například musí natahovat při startu
To pak nevadí ten balast, ale to, že se natahuje při startu.
že v něm bývají chyby
Když jsou to části, které nepoužívám, může mi být úplně jedno, že jsou tam nějaké chyby.
že je to děsivý moloch, který nikdo neví, jak funguje atd. atd.
Pokud je to děsivý moloch, tak to nepoužívejte. A pokud použijete nějakou část, zbytek vás nemusí zajímat. Úplně stejně, jako když to máte implementované v runtime Erlangu.
Lidi nechtějí požadavky zahazovat. Lidi chtějí mít tak výkonné systémy, aby dokázaly všechny požadavky zpracovat - a mít i nějakou rezervu, popř. autoscaling. Zahazování by měla být nejzazší krizová možnost, není to něco, čím by kdokoli chtěl řešit problém.
Já jsem také psal o nejzazší krizové možnosti. Jenže když už k takové situaci dojde, je pořád lepší, když server zvládne obsloužit aspoň nějaké požadavky, než když je plně zaměstnán sám sebou a neodvede vůbec žádnou reálnou práci.
-
To nebude ipso facto schedulerem, ale tím, že tam je kooperativní rozvrhování. Stejně optimálně by to fungovalo v jakémkoliv jazyce nebo prostředí od Go přes GCD po - blahé paměti - WebObjects.
Jasně, já jsem jenom chtěl říct, že v Erlangu typicky bývá hodně malých procesů a ty pak scheduler rozhazuje po dostupných vláknech. Hodně malých procesů má větší pravděpodobnost vlákna vytížit rovnoměrně, čistě statisticky. V jazycích, kde mám obvykle procesů míň, to nebude tak dobře fungovat (ale v principu je to to samý, o to se nehádám).
Já měl taky na mysli případ, kdy je hodně procesů ;)
Když už jsme u toho "zahazování" - v jazycích majících nativně CSP lze napsat optimální load balancer na dva řádky. Erlang neznám, nevím, jestli má posílání zpráv v rámci IPC, ale nejspíš by to šlo stejně snadno jako v Go.
-
Pokud v nějakém jazyce musím explicitně vybírat GC, aby mi program fungoval, tak je něco hodně špatně.
Nevím o jazyku, u kterého byste explicitně vybíral GC. Já jsem psal o JVM, což je běhové prostředí. Také vůbec nebyla řeč o tom, že by program nefungoval. Jenom bylo zmíněno podezření (v diskusi ničím nepodložené), že by GC mohl ovlivňovat výkon aplikace – pak je logické prozkoumat charakteristiku použitého GC a porovnat ji s charakteristikami jiných dostupných GC a případně GC změnit. Na tom, že je v jednom běhovém prostředí dostupných více implementací GC, není nic špatného – každý se chová trochu jinak a hodí se tak pro jiný typ úloh. Například Linux má několik implementací plánovačů procesů, několik implementací plánovačů IO, několik implementací souborových systémů – obecně je to považováno za plus, protože si každý může vybrat, co zrovna on potřebuje, a není odkázán na jedno one size fits all řešení, které bude ve všech případech stejně špatné.
Javu jinde než nad JVM nespustím, že? Problém Javy je, že neumožňuje nějakou aspoň pseudotransparentní alokaci dat na zásobníku. Kdyby tomu tak bylo, nemusel by nikdo vyvíjet kvanta různých GC a ladit je pro každou aplikaci zvlášť.
-
Když jsou to části, které nepoužívám, může mi být úplně jedno, že jsou tam nějaké chyby.
Opsáci to vidí jinak. Stomegové updaty jednou měsíčně, opravující nikdo neví co, miluje každý :)
Pokud je to děsivý moloch, tak to nepoužívejte.
Nepoužívám :)
Já jsem také psal o nejzazší krizové možnosti. Jenže když už k takové situaci dojde, je pořád lepší, když server zvládne obsloužit aspoň nějaké požadavky, než když je plně zaměstnán sám sebou a neodvede vůbec žádnou reálnou práci.
To rozhodně. A právě proto mezi sebou erlangovské procesy komunikují zprávami, které se ukládají do - tramtadadáááá - fronty :)
Ten proces pracuje s nějakými daty. Ta mohou být velká.
Zatímco když se použije fronta, tak budou malá?!
-
Ten proces pracuje s nějakými daty. Ta mohou být velká.
Zatímco když se použije fronta, tak budou malá?!
fronta omezí množství dat zpracovávané současně.
-
Když už jsme u toho "zahazování" - v jazycích majících nativně CSP lze napsat optimální load balancer na dva řádky. Erlang neznám, nevím, jestli má posílání zpráv v rámci IPC, ale nejspíš by to šlo stejně snadno jako v Go.
Nevím, co přesně myslíš "posílání zpráv v IPC". Erlangovské procesy komunikují jenom pomocí zpráv, popř. DB. Navíc mechanismus posílání zpráv v rámci jednoho erlangovského VM nebo víc (třeba přes síť) je stejný, takže je to plně transparentní, dobře se to horizontálně škáluje.
Asi největší rozdíl oproti Go (který znám teda málo...) je v tom, že vybírání zpráv z mailboxu je v Erlangu selektivní - tj. můžu si pomocí patternmatchingu třeba vybrat zprávy, který chci zpracovat přednostně. U Go bych asi (?) musel použít separátní channely, což je míň pohodlný a komplikuje to kód.
-
fronta omezí množství dat zpracovávané současně.
O-M-G!
Tak samozřejmě. Pokud mám 50 req/s a pro každý musím načíst několik MB, tak se můžu dostat do úzkých. Ale to nemá žádné řešení. Pool ani fronta to nijak nevyřeší, maximálně můžou trochu vyhladit špičky.
To rozhodně. A právě proto mezi sebou erlangovské procesy komunikují zprávami, které se ukládají do - tramtadadáááá - fronty :)
-
Když už jsme u toho "zahazování" - v jazycích majících nativně CSP lze napsat optimální load balancer na dva řádky. Erlang neznám, nevím, jestli má posílání zpráv v rámci IPC, ale nejspíš by to šlo stejně snadno jako v Go.
Nevím, co přesně myslíš "posílání zpráv v IPC". Erlangovské procesy komunikují jenom pomocí zpráv, popř. DB. Navíc mechanismus posílání zpráv v rámci jednoho erlangovského VM nebo víc (třeba přes síť) je stejný, takže je to plně transparentní, dobře se to horizontálně škáluje.
Asi největší rozdíl oproti Go (který znám teda málo...) je v tom, že vybírání zpráv z mailboxu je v Erlangu selektivní - tj. můžu si pomocí patternmatchingu třeba vybrat zprávy, který chci zpracovat přednostně. U Go bych asi (?) musel použít separátní channely, což je míň pohodlný a komplikuje to kód.
g Jo, myslel jsem třeba přes síť. Erlang se mi začíná líbit :)
-
Javu jinde než nad JVM nespustím, že?
Existovaly nějaké překladače Javy, nevím, v jakém jsou stavu.
Problém Javy je, že neumožňuje nějakou aspoň pseudotransparentní alokaci dat na zásobníku.
Ne, to problém Javy není.
Kdyby tomu tak bylo, nemusel by nikdo vyvíjet kvanta různých GC a ladit je pro každou aplikaci zvlášť.
Kvanta různých GC nikdo nevyvíjí, nikdo je neladí pro každou aplikaci zvlášť, a GC nepoužívá ani zdaleka jenom Java. Vlastně bude jednodušší vyjmenovat jazyky, které běžně GC nepoužívají (ale kam se občas GC dodává jako knihovna) – C, C++, Pascal.
-
Jo, myslel jsem třeba přes síť. Erlang se mi začíná líbit :)
Tyjo, to's mě dost překvapil, že ho neznáš ani z rychlíku. Určitě na něj koukni, je to extrémně zajímavá věc, minimálně pro studijní účely.
Víc než plain Erlang bych teda doporučil Elixir - je modernější, má zepár modernějších featur (třeba homoikonická, volitelně hygienická makra) a opravuje drobné chybky Erlangu (např. fakt úplně všechno je výraz, to v Erlangu neplatí). Zároveň je s Erlangem plně kompatibilní (asi tak jako Scala s Javou).
-
Tak samozřejmě. Pokud mám 50 req/s a pro každý musím načíst několik MB, tak se můžu dostat do úzkých. Ale to nemá žádné řešení. Pool ani fronta to nijak nevyřeší, maximálně můžou trochu vyhladit špičky.
O vyhlazení špiček právě jde. Fronta nebo pool to vyřeší perfektně.
To rozhodně. A právě proto mezi sebou erlangovské procesy komunikují zprávami, které se ukládají do - tramtadadáááá - fronty :)
bavíme se o na sobě nezávislých úlohách.
-
Javu jinde než nad JVM nespustím, že?
Existovaly nějaké překladače Javy, nevím, v jakém jsou stavu.
Problém Javy je, že neumožňuje nějakou aspoň pseudotransparentní alokaci dat na zásobníku.
Ne, to problém Javy není.
Kdyby tomu tak bylo, nemusel by nikdo vyvíjet kvanta různých GC a ladit je pro každou aplikaci zvlášť.
Kvanta různých GC nikdo nevyvíjí, nikdo je neladí pro každou aplikaci zvlášť, a GC nepoužívá ani zdaleka jenom Java. Vlastně bude jednodušší vyjmenovat jazyky, které běžně GC nepoužívají (ale kam se občas GC dodává jako knihovna) – C, C++, Pascal.
Většina objektů žije jen krátce a neescapují, takže nemá smysl dávat je na haldu a pak likvidovat GC. Doporučuji přečíst si něco o správě paměti (a pak třeba pochopíte, proč se v Javě plánuje umožnit alokaci na zásobníku - i když v Javě 9 už ne - a proč to je velký problém Javy, resp. tedy JVM).
-
Jo, myslel jsem třeba přes síť. Erlang se mi začíná líbit :)
Tyjo, to's mě dost překvapil, že ho neznáš ani z rychlíku. Určitě na něj koukni, je to extrémně zajímavá věc, minimálně pro studijní účely.
Víc než plain Erlang bych teda doporučil Elixir - je modernější, má zepár modernějších featur (třeba homoikonická, volitelně hygienická makra) a opravuje drobné chybky Erlangu (např. fakt úplně všechno je výraz, to v Erlangu neplatí). Zároveň je s Erlangem plně kompatibilní (asi tak jako Scala s Javou).
Jo, kouknu, aspoň zběžně, i když ve frontě mám asi milion dalších věcí, třeba Rust nebo Elm - a času je málo...
-
Většina objektů žije jen krátce a neescapují, takže nemá smysl dávat je na haldu a pak likvidovat GC.
Což je ale něco úplně jiného, než co jste psal předtím. Jinak ty různé GC v JVM se liší mimo jiné tím, jak zacházejí s objekty, které mají krátkou životnost. Třeba se jednou dočkáte i v JVM GC, který umožní používat i zásobník.
problém Javy, resp. tedy JVM
Možná byste si měl ujasnit rozdíl mezi programovacím jazykem a virtuálním strojem – místo poučování, co by si kdo měl přečíst. Aspoň že jste to dal na dvouapůltý pokus.
-
O vyhlazení špiček právě jde.
Řekl kdo? Třeba o ně vůbec nejde.
bavíme se o na sobě nezávislých úlohách.
A?
Jo, kouknu, aspoň zběžně, i když ve frontě mám asi milion dalších věcí, třeba Rust nebo Elm - a času je málo...
Rust ti schvaluju, ze seriálu Pavla Tišnovského mě taky zaujal :) Ale Elixir si dej před Elm. Elm je jenom takový "zjednodušený Haskell pro web" - oproti Haskellu tam nic moc novýho nevykoukáš, Elixir, resp OTP je daleko zajímavější ;)
-
Většina objektů žije jen krátce a neescapují, takže nemá smysl dávat je na haldu a pak likvidovat GC.
Což je ale něco úplně jiného, než co jste psal předtím. Jinak ty různé GC v JVM se liší mimo jiné tím, jak zacházejí s objekty, které mají krátkou životnost. Třeba se jednou dočkáte i v JVM GC, který umožní používat i zásobník.
"Hezky" jste přešel, proč si Oracle myslí, že nemožnost explicitně používat zásobník je zásadní problém, pročež plánuje tuto možnost přidat. Až vyjde Java 10, určitě se od všech těch mediocre programmers, jimž je Java určena, dozvíme, jak skvěle se ten jejich jazyk vyvíjí a proč je alokace na zásobníku super. Sekta...
-
O vyhlazení špiček právě jde.
Řekl kdo? Třeba o ně vůbec nejde.
bavíme se o na sobě nezávislých úlohách.
A?
Jo, kouknu, aspoň zběžně, i když ve frontě mám asi milion dalších věcí, třeba Rust nebo Elm - a času je málo...
Rust ti schvaluju, ze seriálu Pavla Tišnovského mě taky zaujal :) Ale Elixir si dej před Elm. Elm je jenom takový "zjednodušený Haskell pro web" - oproti Haskellu tam nic moc novýho nevykoukáš, Elixir, resp OTP je daleko zajímavější ;)
Haskell jde nějak zjednodušit? ??? :-\ :o
-
Haskell jde nějak zjednodušit? ??? :-\ :o
Jo. Elm nemá typeclasses. Takže nemá ani obecné monády. Pro každý typ je potřeba monádu napsat zvlášť - např. http://package.elm-lang.org/packages/elm-lang/core/5.1.1/Json-Decode#andThen
-
Haskell jde nějak zjednodušit? ??? :-\ :o
Jo. Elm nemá typeclasses. Takže nemá ani obecné monády. Pro každý typ je potřeba monádu napsat zvlášť - např. http://package.elm-lang.org/packages/elm-lang/core/5.1.1/Json-Decode#andThen
Kromě Haskellu neznám typovaný jazyk s obecnými monádami (ani ve Swiftu to nejde), takže to asi přežiju. No nic, jdu na pláž, přeju hodně sil v boji s duševním polotovarem ;)
-
Zkusme si shrnou pár základních faktů:
- server běží nad ARM64
- je to velmi jednoduchý server, v podstatě asi dotaz do databáze nebo IPC a serializace/deserializace JSON
- existuje proof of concept v C (ještě nikdy jsem neviděl PoC v low-level jazyce, což opět indikuje relativně jednoduché řešení)
- autor má velkou vůli to přepsat a naučit se něco nového
Nevíme:
- zda DB běží na stejném zařízení
Za dobu, co tady diskutujete bych to s největší pravděpodobností už měl přepsané. :)
Takže mých 0.005c:
1. Určitě není špatná rada zjistit, kde to drhne. Pokud s tím nemáš zkušenosti, je to výzva naučit se něco nového
2. Určitě není vyloženě špatný nápad to přepsat do něčeho jiného (zvláště pokud je to ARM64). Někteří masochisté sice propagují Javu i na RPi, ale nejlepší nápad to většinou není
3. Z toho co víme (C, Java) si myslím, že nejméně problematické bude Go.
a) je to velmi jednoduchý jazyk s téměř identickou syntaxí, se znalostí C a Javy lze po přečtení tutoriálu (cca 2h) najít nějaký příklad a začít psát
b) je určen přesně pro toto použití
c) má extrémně malé paměťové nároky a je překládán přímo do strojového kódu
d) má neuvěřitelně jednoduchou křížovou kompilaci, takže lze vyvíjet na vlastním stroji a spouštět a testovat na ARM
e) jeho GC je optimalizován na latenci, takže žádné stop the world na 2s nehrozí :)
Osobně to odhaduji, že ačkoliv začátečník, přes víkend to budeš mít hotové. Pokud jsem to odhadl dobře, bude to mít celé do 500 řádků.
Pokud bys potřeboval poradit, dej tady vědět.
Pro ostatní:
Netvrdím, že Go je jediné nebo nejlepší řešení. Jen říkám, že z výše uvedených důvodů je to určitě velmi dobré řešení. A s největší pravděpodobností problémy zmizí "samy" i bez toho profilování. Celkové paměťové nároky budou odhadem 10-20x menší.
-
Zkusme si shrnou pár základních faktů:
- server běží nad ARM64
- je to velmi jednoduchý server, v podstatě asi dotaz do databáze nebo IPC a serializace/deserializace JSON
- existuje proof of concept v C (ještě nikdy jsem neviděl PoC v low-level jazyce, což opět indikuje relativně jednoduché řešení)
- autor má velkou vůli to přepsat a naučit se něco nového
Nevíme:
- zda DB běží na stejném zařízení
Za dobu, co tady diskutujete bych to s největší pravděpodobností už měl přepsané. :)
Takže mých 0.005c:
1. Určitě není špatná rada zjistit, kde to drhne. Pokud s tím nemáš zkušenosti, je to výzva naučit se něco nového
2. Určitě není vyloženě špatný nápad to přepsat do něčeho jiného (zvláště pokud je to ARM64). Někteří masochisté sice propagují Javu i na RPi, ale nejlepší nápad to většinou není
3. Z toho co víme (C, Java) si myslím, že nejméně problematické bude Go.
a) je to velmi jednoduchý jazyk s téměř identickou syntaxí, se znalostí C a Javy lze po přečtení tutoriálu (cca 2h) najít nějaký příklad a začít psát
b) je určen přesně pro toto použití
c) má extrémně malé paměťové nároky a je překládán přímo do strojového kódu
d) má neuvěřitelně jednoduchou křížovou kompilaci, takže lze vyvíjet na vlastním stroji a spouštět a testovat na ARM
e) jeho GC je optimalizován na latenci, takže žádné stop the world na 2s nehrozí :)
Osobně to odhaduji, že ačkoliv začátečník, přes víkend to budeš mít hotové. Pokud jsem to odhadl dobře, bude to mít celé do 500 řádků.
Pokud bys potřeboval poradit, dej tady vědět.
Pro ostatní:
Netvrdím, že Go je jediné nebo nejlepší řešení. Jen říkám, že z výše uvedených důvodů je to určitě velmi dobré řešení. A s největší pravděpodobností problémy zmizí "samy" i bez toho profilování. Celkové paměťové nároky budou odhadem 10-20x menší.
ad 2) Na ARM32 je Java nepoužitelná tragédie, na ARM64 to je asi o něco lepší, ale stejně bych se tomu obloukem vyhnul.
ad 3) Rozhodně to bude snazší než to psát v C nad kqueue a GCD. Pokud je problém GC, tak se fakt vyřeší sám.
-
No nic, jdu na pláž, přeju hodně sil v boji s duševním polotovarem ;)
Abysme si rozuměli, mně se Elm moc líbí a používám ho rád. Protože nejsem haskellista, tak mi absence typeclasses zas tak moc nevadí, prostě se občas duplikuje kód, ale zas je aspoň jednodušší a není "přeabstrahováno", což mně u Haskellu občas trochu vadí (pokud to člověk nemá všechno v hlavě, musí sestoupit postupně několik vrstev abstrakce, aby zjistil, co ten kód vlastně dělá).
Akorát Elm není pro člověka, který aspoň trochu zná Haskell, moc zajímavý z hlediska studia. Zajímavý je jenom podívat se, co zjedodušili a jaké to má pro webový vývoj důsledky. Jinak tam myslím není nic moc, co by nebylo v Haskellu.
-
Zkusme si shrnou pár základních faktů:
- server běží nad ARM64
- je to velmi jednoduchý server, v podstatě asi dotaz do databáze nebo IPC a serializace/deserializace JSON
- existuje proof of concept v C (ještě nikdy jsem neviděl PoC v low-level jazyce, což opět indikuje relativně jednoduché řešení)
- autor má velkou vůli to přepsat a naučit se něco nového
Nevíme:
- zda DB běží na stejném zařízení
Za dobu, co tady diskutujete bych to s největší pravděpodobností už měl přepsané. :)
Takže mých 0.005c:
1. Určitě není špatná rada zjistit, kde to drhne. Pokud s tím nemáš zkušenosti, je to výzva naučit se něco nového
2. Určitě není vyloženě špatný nápad to přepsat do něčeho jiného (zvláště pokud je to ARM64). Někteří masochisté sice propagují Javu i na RPi, ale nejlepší nápad to většinou není
3. Z toho co víme (C, Java) si myslím, že nejméně problematické bude Go.
a) je to velmi jednoduchý jazyk s téměř identickou syntaxí, se znalostí C a Javy lze po přečtení tutoriálu (cca 2h) najít nějaký příklad a začít psát
b) je určen přesně pro toto použití
c) má extrémně malé paměťové nároky a je překládán přímo do strojového kódu
d) má neuvěřitelně jednoduchou křížovou kompilaci, takže lze vyvíjet na vlastním stroji a spouštět a testovat na ARM
e) jeho GC je optimalizován na latenci, takže žádné stop the world na 2s nehrozí :)
Osobně to odhaduji, že ačkoliv začátečník, přes víkend to budeš mít hotové. Pokud jsem to odhadl dobře, bude to mít celé do 500 řádků.
Pokud bys potřeboval poradit, dej tady vědět.
Pro ostatní:
Netvrdím, že Go je jediné nebo nejlepší řešení. Jen říkám, že z výše uvedených důvodů je to určitě velmi dobré řešení. A s největší pravděpodobností problémy zmizí "samy" i bez toho profilování. Celkové paměťové nároky budou odhadem 10-20x menší.
ad 2) Na ARM32 je Java nepoužitelná tragédie, na ARM64 to je asi o něco lepší, ale stejně bych se tomu obloukem vyhnul.
ad 3) Rozhodně to bude snazší než to psát v C nad kqueue a GCD. Pokud je problém GC, tak se fakt vyřeší sám.
Hlavne by som najprv vyskusal vyhodit openjdk a dat tam javu od oracle. Teda, ako to pytajuci sa este neurobil. To moze spravit aj 10-nasobny rozdiel. Na x86 je openjdk s vykonom zhruba zarovno, na ARM to vsak neplati.
-
Zkusme si shrnou pár základních faktů:
- server běží nad ARM64
- je to velmi jednoduchý server, v podstatě asi dotaz do databáze nebo IPC a serializace/deserializace JSON
- existuje proof of concept v C (ještě nikdy jsem neviděl PoC v low-level jazyce, což opět indikuje relativně jednoduché řešení)
- autor má velkou vůli to přepsat a naučit se něco nového
Nevíme:
- zda DB běží na stejném zařízení
Za dobu, co tady diskutujete bych to s největší pravděpodobností už měl přepsané. :)
Takže mých 0.005c:
1. Určitě není špatná rada zjistit, kde to drhne. Pokud s tím nemáš zkušenosti, je to výzva naučit se něco nového
2. Určitě není vyloženě špatný nápad to přepsat do něčeho jiného (zvláště pokud je to ARM64). Někteří masochisté sice propagují Javu i na RPi, ale nejlepší nápad to většinou není
3. Z toho co víme (C, Java) si myslím, že nejméně problematické bude Go.
a) je to velmi jednoduchý jazyk s téměř identickou syntaxí, se znalostí C a Javy lze po přečtení tutoriálu (cca 2h) najít nějaký příklad a začít psát
b) je určen přesně pro toto použití
c) má extrémně malé paměťové nároky a je překládán přímo do strojového kódu
d) má neuvěřitelně jednoduchou křížovou kompilaci, takže lze vyvíjet na vlastním stroji a spouštět a testovat na ARM
e) jeho GC je optimalizován na latenci, takže žádné stop the world na 2s nehrozí :)
Osobně to odhaduji, že ačkoliv začátečník, přes víkend to budeš mít hotové. Pokud jsem to odhadl dobře, bude to mít celé do 500 řádků.
Pokud bys potřeboval poradit, dej tady vědět.
Pro ostatní:
Netvrdím, že Go je jediné nebo nejlepší řešení. Jen říkám, že z výše uvedených důvodů je to určitě velmi dobré řešení. A s největší pravděpodobností problémy zmizí "samy" i bez toho profilování. Celkové paměťové nároky budou odhadem 10-20x menší.
ad 2) Na ARM32 je Java nepoužitelná tragédie, na ARM64 to je asi o něco lepší, ale stejně bych se tomu obloukem vyhnul.
ad 3) Rozhodně to bude snazší než to psát v C nad kqueue a GCD. Pokud je problém GC, tak se fakt vyřeší sám.
Hlavne by som najprv vyskusal vyhodit openjdk a dat tam javu od oracle. Teda, ako to pytajuci sa este neurobil. To moze spravit aj 10-nasobny rozdiel. Na x86 je openjdk s vykonom zhruba zarovno, na ARM to vsak neplati.
Urobil som to ja. Na ARM32 řádově pomalejší (nepoužitelné) obě. ARM64 oraclí zvládá lépe, ale furt napikaču na rozdíl od amd64. JIT prostě ARM nedává.
-
Urobil som to ja. Na ARM32 řádově pomalejší (nepoužitelné) obě. ARM64 oraclí zvládá lépe, ale furt napikaču na rozdíl od amd64. JIT prostě ARM nedává.
No, ale stale moze byt vykon dostatocny, mne to na rpi behalo celkom slusne. Podrobne vykonove testy som nerobil. Pre moje ucely to vsak stacilo, mal som tam servis deploynuty na spring boot.
Oracle java na ARM daval ovela lepsie vysledky, nez openjdk. Co urobil zboj ma az tak nezaujima. Zaujima ma, ci autor povodneho prispevku skusil oracle javu miesto openjdk. Mozno by mu to usetrilo robotu v prepisovani do brainfucku.
-
Může mi někdo prosím poradit, jakým způsobem přepsat server? Kontext: mám webovou službu, rozhraní je přes JSON, server je napsaný v Javě (přímo nad standardní knihovnou, žádný framework), kód je malý (nějaké základní zpracování dat, IPC k jedné lokální komponentě a přístup do databáze), ale požadavků není málo (tisíce za minutu) a současná verze je dost náročná na paměť a občas se zasekává (asi GC). Koukal jsem na node.js, ale jednovláknovost se mi moc nepozdává (server má ARM64 s 16 vlákny). Mám na přepsání čas a chuť experimentovat, jen si nejsem jistý, jakým směrem se vydat (mám prototyp v čistém C nad syscally, ale nedal bych ruku do ohně za spolehlivost, je to jen proof of concept).
Šlo by pls. ten server pustit s profilerem a získat víc info o tom, kde se to skutečně brzdí? Možná i pustit to s volbou -verbose:gc, ať je vidět, jestli má skutečně problém GC (může být, zrovna ta serializace/deserializace JSONu asi bude dělat mnoho stringů).
-
Přesně tak, podle mě je nerozum to přepisovat aniž bych věděl, kde to drhne. Mně se osvědčil JVM Monitor doinstalovaný do Eclipse, kterým jsem se připojil na běžící aplikaci a zjistil, kde aplikace tráví většinu času - v call tree to bylo na pár kliknutí vidět. Použil jsem profilování pomocí samplingu, protože bytecode instrumentace trvala zaprvé hrozně dlouho a zadruhé se s ním aplikace nevyrovnala. Problém byl pak vyřešen asi za hodinu nepatrnou úpravou kódu :-)
Předpokládám, že by tohle šlo udělat po síti i na tom ARMu. Zkoušel jsem i Visual VM, ale nenašel jsem tam tak call tree, bez kterého bych úzké hrdlo asi nenašel (neměl jsem problém v pamětí, ale s rychlostí).
-
A ještě k té záměně JVM.
Už podle slov autora vlákna není zjevně problém ve verzi JVM, ale spíš v architektuře aplikace. Pokud na server chodí vyšší desítky požadavků za vteřinu, přičemž každý požadavek = jeden thread, pro zlepšení bude s největší pravděpodobností potřeba přepsat i tu Java aplikaci. Samozřejmě to může drhnout na mnoha místech, nikde se nezmiňuje charakter těch požadavků (sběr dat => zápis nebo spíš čtení).
Takže pokud by se to přepisovalo tak jako tak, je otázka jestli zůstat u Javy velice aktuální, zvláště pak v případě nutnosti učit se třeba nějaký framework.
-
Takže pokud by se to přepisovalo tak jako tak
Upravit aplikaci tak, aby nepoužívala nové vlákno pro každý požadavek, ale aby se používal pool vláken nebo asynchronní IO, přece neznamená přepsat celou aplikaci.
-
A ještě k té záměně JVM.
Už podle slov autora vlákna není zjevně problém ve verzi JVM, ale spíš v architektuře aplikace. Pokud na server chodí vyšší desítky požadavků za vteřinu, přičemž každý požadavek = jeden thread, pro zlepšení bude s největší pravděpodobností potřeba přepsat i tu Java aplikaci. Samozřejmě to může drhnout na mnoha místech, nikde se nezmiňuje charakter těch požadavků (sběr dat => zápis nebo spíš čtení).
Takže pokud by se to přepisovalo tak jako tak, je otázka jestli zůstat u Javy velice aktuální, zvláště pak v případě nutnosti učit se třeba nějaký framework.
Než řešit výběr JVM, GC a nevím co ještě, to je fakt lepší to přepsat do něčeho moderního.
-
Než řešit výběr JVM, GC a nevím co ještě, to je fakt lepší to přepsat do něčeho moderního.
Schopní programátoři najdou úzké hrdlo aplikace a to opraví. Lopaty přepisují celou aplikaci do "modernějšího".
-
Než řešit výběr JVM, GC a nevím co ještě, to je fakt lepší to přepsat do něčeho moderního.
Schopní programátoři najdou úzké hrdlo aplikace a to opraví. Lopaty přepisují celou aplikaci do "modernějšího".
protože aplikace jsou zásadně obecně dobře navržené a technologie vhodně zvolené :)
-
pro zajímavost, dva miliony a jedno vlákno inkrementují celé číslo:
{-
ghc -threaded -rtsopts threadring.hs
./threadring +RTS -K16M -N1
12.526375s
"..."
1.328629s
1.25943s
1.257285s
-}
import Control.Monad
import Control.Concurrent
import Data.Time
spawn 0 c = return c
spawn i input = do
output <- newEmptyMVar
forkIO $ forever $
takeMVar input
>>= return . (+1)
>>= putMVar output
spawn (i - 1) output
main = do
t0 <- getCurrentTime
first <- newEmptyMVar
last <- spawn 2000000 first
getCurrentTime >>= print . flip diffUTCTime t0
print "..."
forever $ do
t0' <- getCurrentTime
putMVar first 0
takeMVar last
getCurrentTime >>= print . flip diffUTCTime t0'
-
protože aplikace jsou zásadně obecně dobře navržené a technologie vhodně zvolené :)
Nevěřím, že by Zboj zvolil vhodnější technologii.
-
Než řešit výběr JVM, GC a nevím co ještě, to je fakt lepší to přepsat do něčeho moderního.
Aha, takže je lepší nejdřív řešit výběr něčeho moderního, pak se naučit něco moderního, přepsat to, a teprve pak řešit výběr VM, GC a nevím co ještě. To se opravdu vyplatí.
Víte, ono to „moderní“ buď bude specializované na tenhle typ úlohy – jenže pak musíte nejprve najít ten správný specializovaný jazyk/nástroj. Pak hrozí, že bude tak úzce specializovaný, že v něm nikdo nic nebude psát a zanikne. Nebo „jenom“ to, že už v něm vy nikdy nenapíšete nic jiného. Nebo prostě jen zůstanete v daném jazyce amatérem. Nebo to „moderní“ bude obecný nástroj, a pak jej zase budete muset nakonfigurovat pro konkrétní použití. Ono totiž vůbec nejde o to, jestli je to „moderní“ nebo „nemoderní“, ale o to, že obecné nástroje jsou prostě obecné, takže je pro konkrétní použití musíte přizpůsobit.
-
Ono totiž vůbec nejde o to, jestli je to „moderní“ nebo „nemoderní“, ale o to, že obecné nástroje jsou prostě obecné, takže je pro konkrétní použití musíte přizpůsobit.
čili obecné nástroje byly vytvořeny již dokonalé a nové/lepší nevznikají :)
-
Pokud je čas a chuť to přepsat do něčeho jiného a nebude vadit že to má někdo jiný udržovat, tak by byl hřích to nevyužít.
V tomto případě je Go nejlepší volba, protože je to jazyk (resp. "platforma") přesně pro tento účel.
Něco jiného je někde ve firmě, kde se řeší věci jako náklady nebo zastupitelnost. Tam pak platí, že by se mělo zjistit co je přesně špatně a podle toho pokračovat.
-
Ono totiž vůbec nejde o to, jestli je to „moderní“ nebo „nemoderní“, ale o to, že obecné nástroje jsou prostě obecné, takže je pro konkrétní použití musíte přizpůsobit.
čili obecné nástroje byly vytvořeny již dokonalé a nové/lepší nevznikají :)
Vznikají, ale zrovna zrovna Go není obecný nástroj. Vzniklo pro řešení jednoho konkrétního typu úloh, obecné programování je v tom zbytečně pracné.
-
čili obecné nástroje byly vytvořeny již dokonalé a nové/lepší nevznikají :)
Nikoli. Ale to, že je něco nového, ještě neznamená, že je to lepší a obecné. Navíc i spousta těch „starých“ nástrojů se pořád vyvíjí, vyvíjí se i způsob práce s nimi.
Aby to někdo špatně nepochopil, já vůbec nejsem proti novým jazykům nebo nástrojům. Pokud někdo má nějaké zadání a rozumí mu natolik, že podle něj napsal program, a teď má čas a chuť to naprogramovat znova, je to ideální příležitost pro vyzkoušení si nového nástroje nebo jazyka (a zároveň trochu past, protože se nejspíš bude pokoušet některé věci řešit stejně, jako by je řešil v tom původním nástroji – opravdový programátor v Cobolu je schopen v Cobolu programovat v jakémkoli jazyce).
Ale mírnil bych to nadšení pro přepis a pro „moderní“ jazyky. Tím, že se něco jenom přepíše, se nic nezíská (kromě nových chyb v kódu). Nic se nezíská ani tím, že se to jen přepíše do „něčeho modernějšího“. Získá se například tím, že se změní architektura – a když už se bude přepisovat architektura, může se jako vedlejší efekt zvolit i jiný jazyk.
-
Pokud je čas a chuť to přepsat do něčeho jiného a nebude vadit že to má někdo jiný udržovat, tak by byl hřích to nevyužít.
V tomto případě je Go nejlepší volba, protože je to jazyk (resp. "platforma") přesně pro tento účel.
Něco jiného je někde ve firmě, kde se řeší věci jako náklady nebo zastupitelnost. Tam pak platí, že by se mělo zjistit co je přesně špatně a podle toho pokračovat.
V Go to bude z obecných jazyků nejsnadnější. Kdo má chuť experimentovat, může ještě zkusit GCD, když už je verze v C.
-
Než řešit výběr JVM, GC a nevím co ještě, to je fakt lepší to přepsat do něčeho moderního.
Pokud je čas a chuť to přepsat do něčeho jiného a nebude vadit že to má někdo jiný udržovat, tak by byl hřích to nevyužít.
V tomto případě je Go nejlepší volba, protože je to jazyk (resp. "platforma") přesně pro tento účel.
Něco jiného je někde ve firmě, kde se řeší věci jako náklady nebo zastupitelnost. Tam pak platí, že by se mělo zjistit co je přesně špatně a podle toho pokračovat.
V Go to bude z obecných jazyků nejsnadnější. Kdo má chuť experimentovat, může ještě zkusit GCD, když už je verze v C.
Presne tak, a kedze je Go uz zastarale, ja by som to pisal v Pony. Naco traposit s gorutinami, ked mozem mat plnohodnotnych aktorov?
-
Problém Javy je, že neumožňuje nějakou aspoň pseudotransparentní alokaci dat na zásobníku.
Ne, to problém Javy není.
Mělo by být pravidlem nepsat o něčem, čemu nerozumím. Courtesy of the rascal: http://www.infoworld.com/article/3202066/java/jvm-may-get-upgrade-to-support-todays-multicore-processors.html
-
Projekt Valhalla http://www.jesperdj.com/2015/10/04/project-valhalla-value-types/ už pár let běží, snad se jej dočkáme v javě 10. Rozhodně to bude užitečné, zpřísněním typování kódu (value types) i výkonově (právě např. jejich kolekce). Už aby byly...
-
Projekt Valhalla http://www.jesperdj.com/2015/10/04/project-valhalla-value-types/ už pár let běží, snad se jej dočkáme v javě 10. Rozhodně to bude užitečné, zpřísněním typování kódu (value types) i výkonově (právě např. jejich kolekce). Už aby byly...
Ano, tím by Java vstoupila (konečně) do 21. století. Ještě teda chybí typová inference, to je taky opruz, zvlášť když všichni významní konkurenti to mají.
-
Projekt Valhalla http://www.jesperdj.com/2015/10/04/project-valhalla-value-types/ už pár let běží, snad se jej dočkáme v javě 10. Rozhodně to bude užitečné, zpřísněním typování kódu (value types) i výkonově (právě např. jejich kolekce). Už aby byly...
Ano, tím by Java vstoupila (konečně) do 21. století. Ještě teda chybí typová inference, to je taky opruz, zvlášť když všichni významní konkurenti to mají.
Java ji ma, jen ji ma malo. Pouziva se u diamondu.
A ano, je to skutecne jeden z podstatnych opruzu.
-
Projekt Valhalla http://www.jesperdj.com/2015/10/04/project-valhalla-value-types/ už pár let běží, snad se jej dočkáme v javě 10. Rozhodně to bude užitečné, zpřísněním typování kódu (value types) i výkonově (právě např. jejich kolekce). Už aby byly...
Ano, tím by Java vstoupila (konečně) do 21. století. Ještě teda chybí typová inference, to je taky opruz, zvlášť když všichni významní konkurenti to mají.
Java ji ma, jen ji ma malo. Pouziva se u diamondu.
A ano, je to skutecne jeden z podstatnych opruzu.
Ano, myslel jsem na úrovni konkurence. Hlavně že se shodneme. Osobně mě to teda už netrápí, protože za problém považuji hlavně molochovitost JVM, ale čistě z pohledu jazyka by stačila ta inference.
-
Kromě Valhally bych si dovolil upozornit na následující:
Typová inference pro lokální proměnné: http://openjdk.java.net/jeps/286
Pattern matching: http://openjdk.java.net/jeps/305
Declaration-site variance: http://openjdk.java.net/jeps/300
-
Typová inference pro lokální proměnné: http://openjdk.java.net/jeps/286
K čemu je dobrá typová inference? Když místo "var" použiji název rozhraní, tak mám jistotu, že mohu s objektem přes toto rozhraní pracovat. Používání rozhraní ArrayList místo List považuji za hloupost.
-
Typová inference pro lokální proměnné: http://openjdk.java.net/jeps/286
K čemu je dobrá typová inference? Když místo "var" použiji název rozhraní, tak mám jistotu, že mohu s objektem přes toto rozhraní pracovat. Používání rozhraní ArrayList místo List považuji za hloupost.
Deklarovat proměnnou jako rozhraní je koncepční chyba, k tomu rozhrani neslouží (a implementačně to je přímo blbost, při statickém typování to s sebou nese zbytečný overhead).
-
Typová inference pro lokální proměnné: http://openjdk.java.net/jeps/286
K čemu je dobrá typová inference? Když místo "var" použiji název rozhraní, tak mám jistotu, že mohu s objektem přes toto rozhraní pracovat. Používání rozhraní ArrayList místo List považuji za hloupost.
Motas lokalni promenne, kde je to povetsinou celkem burt, a interface metod, kde to uz tak moc burt neni.
-
Typová inference pro lokální proměnné: http://openjdk.java.net/jeps/286
K čemu je dobrá typová inference? Když místo "var" použiji název rozhraní, tak mám jistotu, že mohu s objektem přes toto rozhraní pracovat. Používání rozhraní ArrayList místo List považuji za hloupost.
Motas lokalni promenne, kde je to povetsinou celkem burt, a interface metod, kde to uz tak moc burt neni.
U lokálních objektů přece také potřebuji znát rozhraní, abych věděl, které metody toho objektu mohu volat. Přece to nebudu dolovat reflexí.
-
Typová inference pro lokální proměnné: http://openjdk.java.net/jeps/286
K čemu je dobrá typová inference? Když místo "var" použiji název rozhraní, tak mám jistotu, že mohu s objektem přes toto rozhraní pracovat. Používání rozhraní ArrayList místo List považuji za hloupost.
Motas lokalni promenne, kde je to povetsinou celkem burt, a interface metod, kde to uz tak moc burt neni.
U lokálních objektů přece také potřebuji znát rozhraní, abych věděl, které metody toho objektu mohu volat. Přece to nebudu dolovat reflexí.
Aha, ty jsi ani nepochopil, co je to ta typova inference.
val foo = new Foo(bar);
foo je typu Foo. Rozdil je v tom, ze jsi nemusel Foo psat dvakrat, typ foo za tebe odvodil (inferoval) prekladac. Zadnou reflexi nepotrebujes.
Jeste doplnim: prirazovat muzes libovolny vyraz, ne jen tvorbu noveho objektu. A funguje to porad stejne
val baz = 1.1 * 1.2;
baz
je double
-
Rozdil je v tom, ze jsi nemusel Foo psat dvakrat, typ foo za tebe odvodil (inferoval) prekladac.
Osobně dávám přednost uvedení typu proměnné, vidím ji na první pohled, narozdíl např. při přiřazení vrácené hodnoty metody.
Proměnnou včetně typu i přiřazení vyrobí IDE jednou klávesovou zkratkou, jen následně uvedu její název, přičemž mi často rovnou nabídne ten správný. Přijde mi, že na to má Idea nějakou heuristiku učící se z mého stylu pojmenování proměnných, protože se často trefuje hned první nabídkou.
Ukecanost javy při použití slušného IDE nijak nezdržuje.
-
Rozdil je v tom, ze jsi nemusel Foo psat dvakrat, typ foo za tebe odvodil (inferoval) prekladac.
Osobně dávám přednost uvedení typu proměnné, vidím ji na první pohled, narozdíl např. při přiřazení vrácené hodnoty metody.
Proměnnou včetně typu i přiřazení vyrobí IDE jednou klávesovou zkratkou, jen následně uvedu její název, přičemž mi často rovnou nabídne ten správný. Přijde mi, že na to má Idea nějakou heuristiku učící se z mého stylu pojmenování proměnných, protože se často trefuje hned první nabídkou.
Ukecanost javy při použití slušného IDE nijak nezdržuje.
Někdo třeba považuje za slušné IDE vi.
-
....
Pattern matching: http://openjdk.java.net/jeps/305
Declaration-site variance: http://openjdk.java.net/jeps/300
Láďo díky, velice praktické a užitečné. Škoda, že si na javu 10 ještě počkáme... Ještě kdyby byly rozumnější mixiny, defaultní metody interfacu (i privátní v java 9) jsou pořád jen napůl cesty. A samozřejmě opravdová generika s reifikací, ale to je klasika...
-
Osobně dávám přednost uvedení typu proměnné, vidím ji na první pohled, narozdíl např. při přiřazení vrácené hodnoty metody.
A diamant taky nepouzivas?
Proměnnou včetně typu i přiřazení vyrobí IDE jednou klávesovou zkratkou, jen následně uvedu její název, přičemž mi často rovnou nabídne ten správný. Přijde mi, že na to má Idea nějakou heuristiku učící se z mého stylu pojmenování proměnných, protože se často trefuje hned první nabídkou.
Ano, to pojmenovavani ma IntelliJ dobre zvladnute. IMO o duvod mene jeste mit typ vypsany. (Samozrejme jak kdy. Nekdy je lepsi nepouzivat vsechno. Ale u lokalnich promennych bych vetsinou inferenci preferoval - pro psani i cteni)
Ukecanost javy při použití slušného IDE nijak nezdržuje.
Mne to (casto, ne vzdy) vadi i pri cteni. Podobne jako i bez for each cyklu nebylo psani cyklu tezke - idea ho generovala. Jen kod neni tak primocare citelny.
-
A diamant taky nepouzivas?
?? Proč bych jej nepoužíval? Konkrétní typ vidím na druhé straně.
Ano, to pojmenovavani ma IntelliJ dobre zvladnute. IMO o duvod mene jeste mit typ vypsany. (Samozrejme jak kdy. Nekdy je lepsi nepouzivat vsechno. Ale u lokalnich promennych bych vetsinou inferenci preferoval - pro psani i cteni)
Já mám uvedené typy rád. Ale každý to má jinak, proč ne.
Podobne jako i bez for each cyklu nebylo psani cyklu tezke - idea ho generovala. Jen kod neni tak primocare citelny.
For-each generuje samozřejmě taky včetně správného jména a typu položky (iter + tab), ale to se běžně používá.
-
Podobne jako i bez for each cyklu nebylo psani cyklu tezke - idea ho generovala. Jen kod neni tak primocare citelny.
For-each generuje samozřejmě taky včetně správného jména a typu položky (iter + tab), ale to se běžně používá.
Asi jsem to nerekl dost jasne, takze znovu - ze IDE neco generuje neni moc dobra omluva pro to si to vygenerovat, pokud existuje citelnejsi varianta. Jen se ocividne nedohodneme, zda byva lokalni typova inference ta citelnejsi varianta ;)
-
Jen se ocividne nedohodneme, zda byva lokalni typova inference ta citelnejsi varianta ;)
Ano, a protože osobně dávám přednost variantě s typy, rád si to nechám vygenerovat, ručně bych to napsal úplně stejně, jen podstatně pomaleji. Již v mém prvním příspěvku na toto téma jsem uvedl
Osobně dávám přednost uvedení typu proměnné
-
U lokálních objektů přece také potřebuji znát rozhraní, abych věděl, které metody toho objektu mohu volat. Přece to nebudu dolovat reflexí.
Aha, ty jsi ani nepochopil, co je to ta typova inference.
val foo = new Foo(bar);
foo je typu Foo. Rozdil je v tom, ze jsi nemusel Foo psat dvakrat, typ foo za tebe odvodil (inferoval) prekladac. Zadnou reflexi nepotrebujes.
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
-
Mimochodem lze očekávat, že po zavedení lokální typové inference bude idea nabízet generování obou variant, takže opět to půjde rychleji.
-
Mimochodem lze očekávat, že po zavedení lokální typové inference bude idea nabízet generování obou variant, takže opět to půjde rychleji.
O tom nepochybuji... Extract local variable už teď funguje v IntelliJ celkem pěkně v obou variantách (final i nefinal).
-
Celou dobu to tu říkám :-)
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
Za normálních okolností uvedu na levé straně rozhraní a je to.
Interface foo = (cond) ? new Foo() : new Bar();
foo.method();
Možná si tohle umí inference udělat sama, zatím jsem ji nepotřeboval.
-
Za normálních okolností uvedu na levé straně rozhraní a je to.
Interface foo = (cond) ? new Foo() : new Bar();
foo.method();
A jake "je to"? Kazdy vyraz ma nejaky typ, jestli je nasledne pouzity nebo neni pouzity v inferenci je uplne jedno. Zrovna s interfacem ti tohle nemuze v Jave obecne projit.
ALe libi se mi, jak se zacnes dohadovat o veci, o ktere jsi jeste pred hodinou ani nevedel, ze existuje/co dela.
-
Za normálních okolností uvedu na levé straně rozhraní a je to.
Interface foo = (cond) ? new Foo() : new Bar();
foo.method();
A jake "je to"? Kazdy vyraz ma nejaky typ, jestli je nasledne pouzity nebo neni pouzity v inferenci je uplne jedno. Zrovna s interfacem ti tohle nemuze v Jave obecne projit.
V Javě to funguje normálně, stejně jako v PHP. Je to standardní součástí designu Javy. Zkus si to.
-
Za normálních okolností uvedu na levé straně rozhraní a je to.
Interface foo = (cond) ? new Foo() : new Bar();
foo.method();
A jake "je to"? Kazdy vyraz ma nejaky typ, jestli je nasledne pouzity nebo neni pouzity v inferenci je uplne jedno. Zrovna s interfacem ti tohle nemuze v Jave obecne projit.
V Javě to funguje normálně, stejně jako v PHP. Je to standardní součástí designu Javy. Zkus si to.
Eh, v tomhle (Interface foo muze dodat ve specifickem pripade vic informace nez samotna inference typu) mas pravdu. To jsem pomotal, omlouvam se.
-
V Javě to funguje normálně, stejně jako v PHP. Je to standardní součástí designu Javy. Zkus si to.
Eh, v tomhle (Interface foo muze dodat ve specifickem pripade vic informace nez samotna inference typu) mas pravdu. To jsem pomotal, omlouvam se.
V pohodě. Inference je v PHP běžná, jen jsem nevěděl, že se dostala už i do Javy.
-
[V pohodě. Inference je v PHP běžná, jen jsem nevěděl, že se dostala už i do Javy.
Type inference v PHP? O tom bych rád slyšel detaily...
-
[V pohodě. Inference je v PHP běžná, jen jsem nevěděl, že se dostala už i do Javy.
Type inference v PHP? O tom bych rád slyšel detaily...
Já si zase počkám, zda bude Kit taky takovej frajer jako Nekola, a uzná chybu.
-
Já si zase počkám, zda bude Kit taky takovej frajer jako Nekola, a uzná chybu.
Koukam, ze latka na to byt frajer je v posledni dobe dost nizko :-D
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
Tak já bych řekl, že buď vezme největší společný rozhraní, nebo spíš chcípne, protože je to otevřené. (Ale čerpám na základě zkušeností z Haskellu, Java tu interferenci nemá.)
Ale když by se to napsalo takhle:
void foo(Bool cond) {
val foo = (cond) ? new Foo() : new Bar();
foo.method();
}
Tak má všechny potřebné informace co potřebuje, a mohlo by to projít. (Když by to uměla.)
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
Tak já bych řekl, že buď vezme největší společný rozhraní, nebo spíš chcípne, protože je to otevřené. (Ale čerpám na základě zkušeností z Haskellu, Java tu interferenci nemá.)
Typicky se bere prostě supremum, pokud typový systém tvoří úplný svaz. Nebo to je prostě chyba, když se výsledný typ neuvede explicitně, záleží na jazyku. Haskell je v tomto trochu specifický, když má de facto jen rozhraní.
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
Tak já bych řekl, že buď vezme největší společný rozhraní, nebo spíš chcípne, protože je to otevřené. (Ale čerpám na základě zkušeností z Haskellu, Java tu interferenci nemá.)
Typicky se bere prostě supremum, pokud typový systém tvoří úplný svaz. Nebo to je prostě chyba, když se výsledný typ neuvede explicitně, záleží na jazyku. Haskell je v tomto trochu specifický, když má de facto jen rozhraní.
Stačilo říct: "jo" :-)
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
Tak já bych řekl, že buď vezme největší společný rozhraní, nebo spíš chcípne, protože je to otevřené. (Ale čerpám na základě zkušeností z Haskellu, Java tu interferenci nemá.)
Typicky se bere prostě supremum, pokud typový systém tvoří úplný svaz. Nebo to je prostě chyba, když se výsledný typ neuvede explicitně, záleží na jazyku. Haskell je v tomto trochu specifický, když má de facto jen rozhraní.
Stačilo říct: "jo" :-)
Nestačilo, protože to chtělo opravit a upřesnit.
-
A co třeba tohle?
val foo = (cond) ? new Foo() : new Bar();
foo.method();
Jak v takovém případě zafunguje inference? Bude hledat společná rozhraní obou tříd?
A co bys tak rekl? Jaky typ ma tenhle vyraz (cond) ? new Foo() : new Bar();? Nehledej slozitost, kde neni. Nebo se to alespon douc.
Tak já bych řekl, že buď vezme největší společný rozhraní, nebo spíš chcípne, protože je to otevřené. (Ale čerpám na základě zkušeností z Haskellu, Java tu interferenci nemá.)
Typicky se bere prostě supremum, pokud typový systém tvoří úplný svaz. Nebo to je prostě chyba, když se výsledný typ neuvede explicitně, záleží na jazyku. Haskell je v tomto trochu specifický, když má de facto jen rozhraní.
Stačilo říct: "jo" :-)
Nestačilo, protože to chtělo opravit a upřesnit.
Tak to udělej. Vždyť jsi řekl tu samou větu co já, jen jsi použil cizí termity :-D
-
[V pohodě. Inference je v PHP běžná, jen jsem nevěděl, že se dostala už i do Javy.
Type inference v PHP? O tom bych rád slyšel detaily...
Vím, že se tomu tak u dynamicky a slabě typovaných jazyků neříká, ale stejně jsem byl zvědav, kdo se ozve.
-
Pokud se vylozejne nenudist tak nic neprepisovat. Zabere to spoustu casu a vysledek bude podobny. Pohraj si s profilerem (https://visualvm.github.io/ (https://visualvm.github.io/)) a zjisti v cem je problem. Pro paralelni zpracovani requestu pouzij ThreadPool:
https://docs.oracle.com/javase/8/docs/api/java/util/concurrent/ThreadPoolExecutor.html (https://docs.oracle.com/javase/8/docs/api/java/util/concurrent/ThreadPoolExecutor.html)
https://www.javacodegeeks.com/2013/01/java-thread-pool-example-using-executors-and-threadpoolexecutor.html (https://www.javacodegeeks.com/2013/01/java-thread-pool-example-using-executors-and-threadpoolexecutor.html)
Az to bude fungovat jak ma, tak se muzes pustit do prepsani.
-
Tak to mas nieco fakt spatne, lebo s undertow som dal nejako 20000/s (SEKUNDU) ani som nic neladil a uzke hrdlo boli asi nastavenia ab. Go bol na tom velmi podobne a node.js ostalo niekde v prachu.
-
Tak to mas nieco fakt spatne, lebo s undertow som dal nejako 20000/s (SEKUNDU) ani som nic neladil a uzke hrdlo boli asi nastavenia ab. Go bol na tom velmi podobne a node.js ostalo niekde v prachu.
Go by mělo být v tomto optimální, je to bare bones implementace nad nejnižší možnou vrstvou (při zachování bezpečnosti) a má rychlé algoritmy pro HTTPS.
-
Go bol na tom velmi podobne a node.js ostalo niekde v prachu.
Možná proto i sám tvůrce Node.js opustil svůj projekt a přešel na Go (schválně kdo jako první najde referenci).