Muszę stwierdzić, że w blogosferze dzieje się coraz lepiej. Duże firmy wreszcie zaczynają dostrzegać, że to w blogach tkwi o wiele większa siła niż w tradycyjnych mediach. Tą drogą poszła agencja interaktywna Autentika.pl, która zgłosiła się do mnie z pomysłem zorganizowania konkursu.
Sprawa jest prosta, chłopaki z Autentiki szukają front-endowca do ich teamu, jednak uzgodniliśmy, że najlepiej stanie się, jeśli towarzyszyć będzie temu konkurs dla Czytelników, ponieważ z definicji nie wstawiam na tym blogu ogłoszeń o pracę, które nie dotyczą moich projektów. Tak więc wilk syty i owca cała. Co do pracy jeszcze, poznałem kilku ludzi z Autentiki podczas paru eventów i mogę tylko powiedzieć, że znają się na front-endzie, jak mało kto. Poza tym jestem dużym fanem designów przygotowanych przez tę agencję, więc rozmowa była o wiele łatwiejsza.
Co jest do wygrania? JavaScript Patterns Stoyana Stefanova oraz Introducing HTML 5 Remy’ego Sharpa i Bruce’a Lawsona. Myślę, że jest o co walczyć, tym bardziej, że sam polowałem na te książki.
Mamy więc dwa zadania, ułożone przeze mnie razem z Kamilem Trebunią (konkurs dotyczy również Czytelników JSNews.pl). JS Patterns jest nagrodą za pierwsze zadanie, HTML5 za drugie. Udział można wziąć rozwiązując tylko jedno z nich, tak więc musicie dokonać wyboru. Na konkurs mamy dwa tygodnie, na rozwiązania czekam pod damian@jsnews.pl.
Zadanie pierwsze – algorytmiczno-JavaScriptowe.
Wejście:
Jednowymiarowa, posortowana rosnąco tablica unikalnych liczb całkowitych.
Wyjście:
Tablica z niepowtarzającymi się liczbami dodatnimi, których wartość absolutna pojawiła się w tablicy dwa razy.
Przykład:
wejście: [-4, -3, -1, 1, 2, 4, 67]
wyjście: [1, 4]
Opis programu:
Program powinien udostępniać funkcję o nazwie „solve”, dostępną w globalnym scope przeglądarki-środowiska, czyli np.
window.solve = function (input) { [...] return output; };
która powinna przyjmować jeden argument – wejściową tablicę, a na wyjściu powinna zwracać tablicę wynikową. Pozostałe szczegóły implementacji programu są mniej znaczące. Liczy się przede wszystkim dobry styl kodowania (good practices vs bad practices), złożoność czasowa algorytmu oraz szybkość jej JavaScriptowej implementacji. Skrypt sprawdzać będziemy pod Firefox 3.6.14.
W zadaniu drugim zmagać się będziemy z CSS-em.
Należy napisać kod HTML oraz CSS, który wyświetli stronę w układzie 3-kolumnowym. Oznaczmy kolumny literami A, B oraz C.
Kolumna A powinna mieć stałą szerokość „200px”. Kolumny B oraz C powinny być elastyczne, o szerokości zależnej od wielkości ekranu i pozostawać w proporcji 1:2 (kolumna C powinna być dwa razy szersza od kolumny B).
Suma szerokości kolmun A, B oraz C powinna być równa szerokości ekranu – razem, powinny wypełniać całą przestrzeń.
Dodatkowo premiowane będą:
- Szerokość kolumny A powinna być łatwa do zmiany na inną bez przedzierania się przez gąszcz skomplikowanych reguł CSS w których ta wartość występuje w wielu miejscach.
- Weźmy pod uwagę bardzo duże ekrany i załóżmy, że dla ekranów o szerokości większej od 1600px suma szerokości A+B+C będzie wynosić na stałe 1600px (nie będzie się dalej rozszerzać).
- Weźmy pod uwagę niewielkie ekrany (np. telefonów komórkowych) i w przypadku ekranów o szerokości poniżej 640px przyjmijmy, że docelowa treść się w nasz 3-kolumnowy układ nie zmieści. Dodatkowe punkty przyznane będą za poradzenie sobie z tym problemem.
Do Twojej dyspozycji pozostają wszystkie możliwe nowinki, które przynosi nam specyfikacja CSS3 (oraz HTML Living Standard), a które zostały zaimplementowane przynajmniej w Firefox 4 beta lub najnowszych stabilnych buildach przeglądarek Chrome i Safari (pod Windows oraz Mac OS X).



Komentarze
[...] interaktywna Autentika.pl organizuje wraz z Ferrante.pl i JSNews.pl konkurs dla front-endowców, gdzie do wygrania są dwie książki – JavaScript Patterns oraz Introducing [...]
Coś mi tutaj nie pasuje. Skoro A ma stałą szerokość 200px, to B nie może być elastyczne, bo musi mieć 400px, niezależnie od tego, jak bardzo rozciągnę okno przeglądarki. Nie powinno być przypadkiem: „kolumna C powinna być dwa razy większa od kolumny C” ?
Racja, fixed.
Czy po wyłonieniu zwycięzców zamieścicie przygotowany przez nich kod (może nawet z krótkim komentarzem)? Byłoby bardzo fajnie zobaczyć coś zrobionego w porządny sposób.
Tak, zwycięskie kody zostaną opublikowane i omówione (plus inne, jeśli będą jeszcze lepsze/ciekawsze).
Mam pytanie co do wyników zwracanych w postaci tablicy, one też mają być posortowane? Bo to istotna kwestia.
Nie, nie muszą być posortowane.
Mam pytanie w sprawie zadania drugiego. To mniej istotne ale czy ta „strona”ma też zarąbiście wyglądać? Tzn. czy mają mieć backgroundy, gradienty itp. Czy to tez będzie oceniane :)
To chyba oczywiste, że nie.
Wrażenia estetyczne nie mają znaczenia :)
No pracodawcy też patrzą na to czy osoba potrafi ładnie przerobić stronę. Dlatego pytam bo to nie jest takie oczywiste. Ale dzięki za odp.
Posłałem swoje rozwiązanie pierwszego zadania… Obym się nie zbłaźnił :)
Ponad 15 zgłoszeń, zapraszamy wszystkich do zabawy :)
Na dniach podeślę swoje JS :)
Czy będzie można liczyć na ewentualny komentarz od sprawdzających co i jak należałoby poprawić? To oczywiście poza konkursem, profesjonalne wskazówki przydadzą się każdemu.
Wejście należy parsować? Czy można ten element pominąć i skupić się wyłącznie na algorytmie?
mam pytanie odnośnie drugiego zadania ..czy proporcja 1:2 dla kolumn B i C musi się zgadzać co do piksela przy każdej szerokości okna? ..czy wystarczy 34 do 66% ?
@rotflmao – co znaczy parsować wyjście? Wyjście nie musi być posortowane ani nic w tym rodzaju, musi to być tablica z wynikami i tyle :).
@heban – Myślę, ze to dobry pomysł na notkę.
@Winston_Wolf – proporcja będzie wyliczona automatycznie przez browser, więc nie będę przecież mierzył linijką ;-)
@rotflmao: Nie, wystarczy skupić się na algorytmie. Wejście zawsze będzie tablicą która będzie zawierać wyłącznie liczby (żadne stringi itp.).
A ja mam z kolei pytanie innej natury,
chodzi mi o coś w rodzaju ‘zbioru zadań’ z takimi właśnie małymi algorytmicznymi problemami do rozwiązania. Ktoś słyszał, widział, posiada?
Fajnie by było czasem sobie dla rozruszania szarych komórek coś takiego poćwiczyć – ale jeszcze czegoś takiego nie znalazłem…
http://forum.webhelp.pl/javascript/ciekawe-algorytmy-funkcje-i-rozwiazania-t49093.html oraz http://groups.google.com/group/pl.comp.lang.javascript/topics?pli=1 (szukaj po uzytkownikach Vax, Blatek, gandalf)
Post your JSPerf!
FF 3.6.14 : 75,224 ops/sec
Oj, chyba da się lepiej ;-)
155,635 ops/sec
FF 3.6.14
Może ktoś podać sposób jak Wy wyliczacie skuteczność (np. FF 3.6.14 : 75,224 ops/sec), ale tak dokładnie, albo link do jakiegoś tutoriala:) No i czy to zależy od maszyny? Czy testujecie na jakimś kompie online?
manolo: http://jsperf.com – srodowisko, w ktorym bedziemy m.in. testowac skrypty…
i tak, to zalezy od maszyny, os, przegladarki, zadan w tle… wiec wklejanie samego wyniku nie ma sensu ;)
@siemakuba: nieźle!
251,660 ops/sec ;>
FF 3.6.14 @ Ubuntu
Ten sam kod, poprzedni test był z Visty.
Ale ja nie rozumiem (bo nie wiem – a nie chce mi się dowiadywać – jak działa jsperf) co może nam powiedzieć jsperf tutaj. Przecież wyniki się chyba będą różnić w zależności ile elementów będzie miała tablica wejściowa?
Czy liczy się tylko szybkość wykonania skyptu dla tablicy z 7 elementami? Mój algorytm dla 7 elementów nie będzie najszybszy. Ja to testuje przy tablicy z 5000, 10000 elementów.
Może mi ktoś naświetlić sprawę?
Moja wina. Ja myślałem że jsperf jest mniej więcej uregulowany między komputerami.
My Polish isnt so great yet so … It would be awesome if (Kamil or Ferrante) could post a „leaderboard / current best performance” in a standard environment of the top algorithm or top 5 but I understand if it should just be a surprise at the end too. Thanks for the great contest!
Sauveur właśnie sam się nad tym zastanawiam co te ops/sec opisują, ilość instrukcji, szybkość ich wykonania. Testując jsperf każde dodatkowe polecenie spowalnia całość, nawet opakowanie window.solve = function (input) { [...] return output; };, już nie wspomne o uruchomienie samoczynnie czegoś w systemie, ops/sec lecą na łeb na szyję.
Ogólnie pierwszy raz stykam się z tym narzędziem i ciekawi mnie to, jak praktycznie je zastosować do testu. Jakaś notka by się przydała w tej sprawie:) – to tak dla autora bloga w wolnej chwili.
Sam testy robię klasycznie, tablica z elementami np. 100000 czy 200000, Firebug, no i czas od wywołania funkcji do zakończenia działania. Ale widać, że jestem trochę do tyłu w tych nowościach:).
Ja też pierwszy raz z jsperf skorzystałem.
Wynik traktuję jako ciekawostkę, bo jak wspomniano wyżej miarodajne to nie jest zupełnie.
Chociaż, jak sprawdziłem ten sam kod pod Chromium @ Ubuntu, to zobaczyłem wynik 1,041,704 ops/sec. Daje fajny pogląd na szybkość enginów JS w prazeglądarkach.
Jeszcze mam pytanie co do wejścia. Mam rozumieć, że każda liczba (wartość absolutna) może wystąpić na wejściu jako singielka lub para? Tzn, wszelkie tego typu dane wejściowe są błędne:
wejście: [-4,-4, -3, -1, 1, 2, 4, 67]
wejście: [-4,-3, -1, 1, 2,2,2, 4, 67]
wejście: [-4,-3, -1, 1, 2,4, 67,4,5]
?
Czyli sztywne ułożenie w kolejności od najmniejszej do największej bez możliwości powtórzenia tej samej liczby (uwzględniając znak) po sobie? Bo takie założenie wszystko upraszcza:)
Dzięki za podzielenie się linkiem do jsPerf – nieznałem go :)
Wejscie moze byc jakiekolwiek, byle spelnialo warunki tablicy posortowanej rosnaco.
Btw. przyszły już 23 odpowiedzi.
wejście: [-5,-5, -4,-3, -1, 1, 2,2,2, 4, 67]
To też jest posortowane rosnąco, ale czy spełnia warunki założenia, tzn. czy liczby po sobie (uwzględniając znak) mogą się powtarzać?
@manolo
Unikalnych… Czyli nie mogą się powtarzać ;)
Można wysłać dwa rozwiązania do jednego zadania? Bo nie mogę się zdecydować, który sposób lepszy…
@krystian
Zrób test wydajności tych dwóch rozwiązań i zobaczysz które lepsze ;)
245,388 na Core2Duo P8600 2.4GHz ;)
Fx 3.6.15 (srry) + w7 x64
To powyżej dla danych testowych [-4, -3, -1, 1, 2, 4, 67]
A teraz bonus:
>>> input.length
1099420
>>> console.time(‘alg’); window.solve(input); console.timeEnd(‘alg’);
alg: 201ms
O! :)
I jeszcze bez firebuga, równo 1 000 000 unikalnych, posortowanych elementów. Średnia ze 100 prób w pętli: 53.74ms/test… Ciekawostka. Opera 11.10: 35.26ms/test, Chrome 9: 133ms (?!)
Powiem Wam, że przyszło ponad 30 bardzo ciekawych rozwiązań, naprawdę będzie co omawiać :) Jest już nawet jeden zdecydowany lider prędkości.
Dość mało (w porównaniu do 1. zadania) jest zadań CSSowych, tak więc zapraszam :)
Może jakiś ranking top10, żeby podgrzać atmosferę? :)
@pierwsze zadanie – funkcja będzie testowana dla różnych danych wejściowych? jak będziecie wyciągać średnia? różne algorytmy/podejścia lepiej/gorzej radzą sobie w zależności od danych wyjściowych.
Prawie 50 zadań, nice :-)
Jak widać Damian, nie jest z nami źle :)
To jeszcze zadam pytanie odnośnie jspref.
Do testowania w pole Code mam wstawić:
a) całą funkcje z wywołaniem
b) tylko wywołanie funkcji
c) tylko wnętrze funkcji
Zamknięcie przyjmowania zgłoszeń w środę 16.03 ? :)
pytanko do drugiego zadania: czy kolumny zawsze powinny być równej wysokości? czy skoro ten feature nie jest ujęty w poleceniu – olać go, bo i tak nie będzie brany pod uwagę? :)
Zapominalski – Ja wysłałem dopiero dzisiaj (wersja css). Artykuł opublikowany był 2 marca, więc plus dwa tygodnie. W sumie zgadzało by się, że 16 marca. Pisz kod i wysyłaj.
Miałem oba rozwiązane, ale … przeczytałem treść drugi raz treść :)
Wysłałem tylko pierwsze. Myślę, że wiele osób z tych co wysyłali pierwsze spokojnie podołałoby drugiemu.
Też mam oba, ale wysłałem na drugie (żeby nie było, że nikt z css’a pracy nie wysłał).
Konkurs się zakończył – więc może jakieś małe info odn. tego ? Ani na maila ani na blogu ni widu ni slychu …
Wyniki w weekend bądź w przyszłym tygodniu. Bardzo dużo prac dostałem, muszę to przetestować ;-)
[...] zakończył się konkurs front-endowy przy współpracy z Autentika.pl. Przyszło 60 odpowiedzi z czego wiele bardzo [...]
[...] Witam wszystkich czytelników ferrante.pl. W tym gościnnym wpisie omówię pokrótce zwycięskie rozwiązanie konkursu CSS’owego oraz wyjaśnię pewne wątpliwości. Treść zadania znajdziecie we wcześniejszym wpisie. [...]
Poza konkursem:
window.solve = function(arr){
var used = [];
for( var i = 0; i < arr.length; ++i ){
if( arr[i] < 0 ){
used[-arr[i]] = 1;
}else{
if( used[arr[i]] ){
used[arr[i]] = 2;
}
}
}
var res = [];
for( var i in used ){
if( used[i] === 2 ){
res.push(i);
}
}
return res;
}
[...] Na blogu pojawiły się również konkursy. Brawa dla Autentiki, która przetarła szlak i zorganizowała dla Was pierwszy taki konkurs z nagrodami. [...]