Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

10 Stron V  < 1 2 3 4 5 > »   
Closed TopicStart new topic
> Kod doskonały vs rzeczywistość
Pyton_000
post 10.01.2017, 21:21:06
Post #41





Grupa: Zarejestrowani
Postów: 8 068
Pomógł: 1414
Dołączył: 26.10.2005

Ostrzeżenie: (0%)
-----


Przede wszystkim obsługa zapisu/usuwania pliku powinna być oddelegowana do oddzielnej klasy np. StorageHandler(new LocalStorage());
I tam sobie dajesz np.

$storage->store((File)$file);

Czyli defacto masz 2 fabryki: 1 do obsługi pliku samego w sobie a 2 do zapisu/odczytu/usuwania.

Wynikiem 1-szej powinien byc obiekt z którego pobierzesz sobie jakieś tam atrybuty. Wew. niego możesz mieć obiekt np. miniaturki itd itd.
Go to the top of the page
+Quote Post
daro0
post 10.01.2017, 21:31:01
Post #42





Grupa: Zarejestrowani
Postów: 88
Pomógł: 12
Dołączył: 17.09.2014
Skąd: Krasnystaw

Ostrzeżenie: (0%)
-----


Zakładam że są trzy klasy: Uploader_Image, Uploader_Video oraz Uploader_Music, trzy osobne pliki PHP. Zakładam że rozszerzenie będzie w jakiś sposób ustalane na podstawie tego co jest w $_FILES['attachment']['name'] i jest wyciągane i na podstawie np tego:

  1. $files = $_FILES['attachment'];
  2. $path = $_FILES['attachment']['name'];
  3. $ext = pathinfo($path, PATHINFO_EXTENSION);
  4.  
  5. $uploaders = array(
  6. 'jpg' => 'Image',
  7. 'png' => 'Image',
  8. 'gig' => 'Image',
  9. 'bmp' => 'Image',
  10. 'avi' => 'Video',
  11. 'mp4' => 'Video',
  12. 'mp3' => 'Music',
  13. );
  14.  
  15. if (array_key_exists($ext, $uploaders))
  16. {
  17. $uploader = $uploaders[$ext];
  18. $result = Uploader::factory($uploader)
  19. ->data($files)
  20. ->execute();
  21. }
  22. else
  23. {
  24. // jakis komunikat
  25. }
  26.  


To tylko jeden z możliwych sposobów.
Go to the top of the page
+Quote Post
Omenomn
post 10.01.2017, 21:38:41
Post #43





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


ale Wy się cały czas rozszerzeniem zajmujecie, a to jest tylko jeden z problemów i to nie aż tak istotny, nie kumacie, czy nie wiem co...

Opisałem to wcześniej.

Jak daro0 chciałbyś utworzyć tym rozwiązaniem sam obraz, albo obraz z miniaturką?
albo samo wideo, albo wideo z miniaturką, albo wideo z trzema miniaturkami?

Czy dekoracja, sama w sobie nie nasuwa się na myśl?

Masz plik i go dekorujesz, "tu mu zmienię rozmiar, tu mu zmienię rozszerzenie, tu mu zmienię nazwę, tu jeszcze coś innego mu zmienię" biggrin.gif

i tak sobie zmieniam jak mi się podoba.

Tak w ogóle jak czytam te tutoriale z nazwami klas, metod i zmiennych po polsku, to od razu wiem, że taki tutorial to śmieć.
Jaki dobry programista używa polskich nazw w programowaniu.

Ten post edytował Omenomn 10.01.2017, 21:48:42
Go to the top of the page
+Quote Post
Dejmien_85
post 10.01.2017, 22:34:06
Post #44





Grupa: Zarejestrowani
Postów: 251
Pomógł: 23
Dołączył: 23.04.2013

Ostrzeżenie: (0%)
-----


Sądzę, że każdy ma podobne rozterki do Twoich. wink.gif

Pisząc prywatne projekty zawsze biorę pod uwagę "czystość kodu" do "czasu pracy".

Każdy ma jakieś wyobrażenie o tym jaki powinien być kod, a także każdy ma swoje nawyki. Wydaje mi się, że większość z nas ma lepsze wyobrażenie o swojej pracy, niż ona w rzeczywistości wygląda - a widać to najlepiej przy prywatnych projektach. ; )

Uczymy się wzorców, mówimy sobie, że testy i czystość kodu (znana książka "Czysty Kod") są ważne, ale gdy zaczynamy pracę nad jakimś projektem, to nie zawsze trzymamy się idealnie swoich teorii.

Ja osobiście ciągle podejmuję decyzje typu: "zostawić tutaj drobny bałaganik do posprzątania na później czy posprzątać już teraz?".

Najważniejsze to najpierw nauczyć się pokory - pamiętam doskonale czas, kiedy uczyłem się bardzo dużo nt. programowania, wzorców, czystego kodu, testowania. Sam siebie uważałem za wybitnego programistę.
Jednak podczas pewnego projektu śpieszyłem się z dostarczeniem pewnego oprogramowania. Po dwóch miesiącach pisania kodu nagle zdałem sobie sprawę, że złamałem prawie wszystkie zasady, w jakie głęboko
wierzyłem - dostrzegłem wtedy jaką byłem żałosną istotą... ; )

Pomyślałem sobie - Damianie, Ty tępy ch#&$^, uważasz się za tak dobrego programatora, a tutaj tworzysz takie g$%#$, że smród rozchodzi się po całości.

Pamiętam także jedną aplikację, dość dużą. Pisałem ją przez jakiś rok (prywatny projekt). Po długiej przerwie bylem zmuszony do pewnych modyfikacji, zajrzałem więc do starego kodu i...
ni cholery nie mogłem się połapać w jednej części kodu. Po prostu stworzyłem tak cholernie skomplikowany kawałek kodu, że musiałem przez prawie dwie godziny go analizować, aby połapać się
o co w nim chodziło.

Jaka jest moja rada? Nie ma kodu doskonałego. Goni nasz wszystkich czas. Nawet jeśli masz dobre zamiary, to często robisz małe grzeszki. Małe grzeszki nie są złe, o ile się nie rozrastają.

Ze swojej strony powiem tylko tyle, że wszystko zależy od nastroju i nastawienia.

Pisałem prywatne projekty, w których naprawdę działałem według swoich zasad, tj. pełne skupienie na "czystości" i "otestowaniu".
Wielbię Wujka Boba, więc tworzyłem soft otestowany w 90-kilku procentach. Siedziałem nad nim długo, starałem się go ciągle refaktoryzować, nawet gdy
niektóre rozwiązania zabierały dużo czasu. Widziałem tego efekty. Widziałem, że warto mieć testy.

Ale... nawet teraz po latach doświadczenia potrafię się śpieszyć i tworzyć oprogramowanie "na szybko", bez testów, z "małymi grzeszkami".

Ważne, aby mieć jakieś standardy.

Gdy łamię zasady, wtedy coś za uchem mówi mi "grzeszysz". Popełniam grzeszki. Ale mam jednak pewne "standardy grzeszenia".
Mogę pisać kod, który nie jest otestowany. Mogę czasem wprowadzić jakąś mała zawiłość. Ale jesli widzę, że coś staje się zbyt
skomplikowane, albo zbyt nieczytelne, wtedy włącza się alarm i wprowadzam porawki.

W końcu większość z nas wie jakie problemy wiążą się z nieczystym kodem. Doświadczyliśmy tego.
Wiemy co robić, aby nie kopać pod sobą dołków. Czasem grzeszymy. To normalne.

Ważne, aby mieć jakieś normy.
Go to the top of the page
+Quote Post
sazian
post 10.01.2017, 22:34:41
Post #45





Grupa: Zarejestrowani
Postów: 1 045
Pomógł: 141
Dołączył: 19.09.2006
Skąd: B-tów

Ostrzeżenie: (0%)
-----


Cytat(Omenomn @ 10.01.2017, 21:38:41 ) *
Tak w ogóle jak czytam te tutoriale z nazwami klas, metod i zmiennych po polsku, to od razu wiem, że taki tutorial to śmieć.
Jaki dobry programista używa polskich nazw w programowaniu.


Zajrzy do baz danych takich programów jak optima lub xl od comarch-a, subiekt od insert-tu czy wf-mag od wapro.
W ich bazach nie znajdziesz słowa po angielsku, a nie ukrywajmy są to jedne z większych firm w Polsce.
Idąc Twoim tokiem rozumowania ich produkty które zarabiają pewnie niezłe melony to śmieci....
Ale to temat na nieco inną rozmowę wink.gif
Go to the top of the page
+Quote Post
Omenomn
post 10.01.2017, 22:40:36
Post #46





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


Chcesz mi wmówić, że stosowanie polskiego nazewnictwa jest okej?

Zarabianie oprogramowania, nie jest równe z tym, że jest dobrze napisane.
Strony na wordpressie też zarabiają biggrin.gif

Ten post edytował Omenomn 10.01.2017, 22:49:31
Go to the top of the page
+Quote Post
com
post 10.01.2017, 22:46:48
Post #47





Grupa: Zarejestrowani
Postów: 3 034
Pomógł: 366
Dołączył: 24.05.2012

Ostrzeżenie: (0%)
-----


Cytat
Jak daro0 chciałbyś utworzyć tym rozwiązaniem sam obraz, albo obraz z miniaturką?
albo samo wideo, albo wideo z miniaturką, albo wideo z trzema miniaturkami?

Omenomn
A Twoim gdzie niby stwierdzę, że mam wybrać te a nie inne rozwiązanie.

Cytat
Czy dekoracja, sama w sobie nie nasuwa się na myśl?

Nie, za to strategia już tak wink.gif

Przyjrzyjmy się definicji:
Dekorator, pozwala na dynamicznie dodawanie nowych funkcjonalności do istniejących klas podczas działania programu.

Strategia, tworzy wspólny interfejs z dozwolonymi operacjami oraz listę klas implementujących dany interfejs dostarczających konkretne algorytmy.

Factory, dostarcza interfejs do tworzenia obiektów nieokreślonych typów, pozwala podklasom zdecydować, jakiego typu będzie obiekt

I powiedz mi gdzie tu pasuje Twój kod. Co z tego że udekorujesz sobie jakaś klasę jak nie stwierdzisz, że w tym konkretnym miejscu ona ma być tak udekorowana. Pomijając fakt, że zamieniłeś znaczenie modelu w Twoim rozwiązaniu, bo teraz dekorujesz obiekt własnościowi a to miał być podobno upload.
Go to the top of the page
+Quote Post
Omenomn
post 10.01.2017, 23:11:58
Post #48





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


upload, a przed uploadem odpowiednio się plik, a teraz uwaga ------ dekoruje.

Cytat
Dekorator, pozwala na dynamicznie dodawanie nowych funkcjonalności do istniejących klas podczas działania programu.


Własności też, nie tylko funkcjonalności.

Cytat
I powiedz mi gdzie tu pasuje Twój kod. Co z tego że udekorujesz sobie jakaś klasę jak nie stwierdzisz, że w tym konkretnym miejscu ona ma być tak udekorowana. Pomijając fakt, że zamieniłeś znaczenie modelu w Twoim rozwiązaniu, bo teraz dekorujesz obiekt własnościowi a to miał być podobno upload.


Stwierdzę. Kontroler ma metodę przypisaną do routingu, więc jak wyślę coś postem na strona.com/image, to mam w kontrolerze metodę image(), w której wywołuję $image = new PropertyGeter(
new ContentImageGeter(
new ImageNoResizer(
new Encoder(
new FilePuter))));
$image->make($request->file);
i mam upload obrazu,

jak chcę obraz z jego miniaturką to strona.com/image-with-thumbnail, metoda imageWithThumbnail()
$image = new PropertyGeter(
new ContentImageGeter(
new ThumbnailResizer(
new Encoder(
new FilePuter))));
$image->make($request->file);

itd.

Nie potrzebuję wzorca decydującego o tym jaki plik ma zostać stworzony, bo doskonale wiadomo jaki.

http://stackoverflow.com/questions/1234554...e-re-sizing-etc

Ten post edytował Omenomn 10.01.2017, 23:15:07
Go to the top of the page
+Quote Post
com
post 10.01.2017, 23:33:31
Post #49





Grupa: Zarejestrowani
Postów: 3 034
Pomógł: 366
Dołączył: 24.05.2012

Ostrzeżenie: (0%)
-----


Cytat
Własności też, nie tylko funkcjonalności.

To nie moja definicja, ok własności tez mogą być. Ale nie to jest ważne a słowo nowe własności/funkcjonalności.

Spójrz na swój kod i co można tam zauważyć


$image = new PropertyGeter(
new ContentImageGeter(

new ImageNoResizer(
new Encoder(
new FilePuter))));



$image = new PropertyGeter(
new ContentImageGeter(

new ThumbnailResizer(
new Encoder(
new FilePuter))));


95% tego kodu to tak naprawdę spójny interfejs, który mógłby tworzyć jedna całość, a reszta to już tylko odpowiedni wybór ścieżki dla algorytmu.
Cytat
Stwierdzę. Kontroler ma metodę przypisaną do routingu, więc jak wyślę coś postem na strona.com/image

No czyli masz jakaś strategie o niespójnym interfejsie do obsługi i daj to komuś żeby zrozumiał taki kod, a potem użył z nowym schematem bo klient wymyślił sobie że teraz nie 3 miniaturki a 4.

Załóżmy, że piszesz testy, jak taki kod przetestować skoro nie wiesz co tak naprawdę uzyskasz, bo w zależności od tego jak go wywołasz otrzymasz inny wynik, i co jeśli o czymś po drodze zapomnisz, bo dodałes nowe funkcjonalności i zamiast tych 5 dekoratorów masz już ich 20/30/100.

Ten post edytował com 10.01.2017, 23:27:17
Go to the top of the page
+Quote Post
Omenomn
post 10.01.2017, 23:34:13
Post #50





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


No to wtedy robi się nakładkę.

Cytat
Spójrz na swój kod i co można tam zauważyć


  1. $image = new PropertyGeter(
  2. new ContentImageGeter(
  3. new ImageNoResizer(
  4. new Encoder(
  5. new FilePuter))));
  6.  
  7.  
  8. $image = new PropertyGeter(
  9. new ContentImageGeter(
  10. new ThumbnailResizer(
  11. new Encoder(
  12. new FilePuter))));


Co można zauważyć? że za każdym razem jest pobierana właśność do pliku i ustalany content, kodowanie i zapis?

Sprawdź sobie jak wygląda upload video z miniaturką:
  1. $video = new PropertyGeter(
  2. new ThumbnailFromVideoCuter(
  3. new ContentGeter(
  4. new FilePuter)));
  5. $video->make($request->file);

lub samo video. czy inny plik:
  1. $file = new PropertyGeter(
  2. new ContentGeter(
  3. new FilePuter));
  4. $file->make($request->file);


i jakie teraz własności kodu wywnioskowałeś?

Cytat
No czyli masz jakaś strategie o niespójnym interfejsie do obsługi i daj to komuś żeby zrozumiał taki kod, a potem użył z nowym schematem bo klient wymyślił sobie że teraz nie 3 miniaturki a 4.


Każdy framework tak ma, nie wiesz?

Ten post edytował Omenomn 10.01.2017, 23:40:04
Go to the top of the page
+Quote Post
com
post 11.01.2017, 00:46:59
Post #51





Grupa: Zarejestrowani
Postów: 3 034
Pomógł: 366
Dołączył: 24.05.2012

Ostrzeżenie: (0%)
-----


No dokładnie te same dla tej grupy wideo, tak samo będzie dla audio i czego sobie tam jeszcze nie wymyślisz.

Każda grupa to jakiś schemat, który dodatkowo rozbudowujesz i zależnie od tego jak skomponujesz te obiekty taki uzyskasz context, ale dla każdej operacji będzie on inny choć operujesz dalej na tym samym obiekcie, wiec oczekujesz dostać ten obiekt, a nie cokolwiek.

Cytat
Każdy framework tak ma, nie wiesz?


Wskaż mi gdzie framework ma coś nie udokumentowane i nie wiesz co uzyskasz jak wykonasz dany fragment jego kodu.

To trochę tak jakbyś z kota chciał zrobić mysz

To jak się uparłeś już na te twoje "dekoratory" to zrób chociaż Fasade, żeby to można było produktywnie wykorzystać. Tylko to jest trochę bez sensu.

Bo ile teraz ktoś kto chce dodać głupi obrazek musi pamiętać, żeby taki plik dodać. A wzorce maja dawać te możliwość, że jedno rozwiązanie możesz wprost wyjąc z tego projektu i dodać do innego i tam też będzie działać i teraz zamiast kod się sam dokumentować, piszesz how to use.

Dekorator jest rozwiązaniem które można tu zastosować ale tak jak już zostało napisane:
Cytat
Dekoratorem może być tutaj tylko Thumbnail bo on faktycznie coś tam robi na źródłowych danych.


czy jak na tym stacku który podrzucałeś:
  1. process = new Upload(myImage); // concrete component
  2. process = new Resize(process); // decorator
  3. process = new Clip(process); // decorator
  4. process->run();


Cytat
Jak we wzorcu dekorator przekazywać pomiędzy obiektami atrybuty elementu dekorowanego, tak, żeby każda klasa miała do nich dostęp i mogła je modyfikować i, żeby każdy obiekt widział te zmiany.
Tak:

http://blogophp.com/2009/08/16/dekorator/#more-40

Pierwsze co powinno To Cie właśnie zastanowić, że coś jest tutaj nie tak, skoro tak nie jest. Jak już używamy wzorców to trzeba ich używać dobrze, bo inaczej zamiast kod rozjaśnić zaciemniamy go.

Podsumowując, właściwości nie powinny wędrować miedzy dekoratorami, bo wtedy już to nie jest dekorator! Dekorujesz konkrety obiekt bazę która rozszerzasz, a nie budujesz nad obiektem bazy nowego obiektu do rozszerzeń. Każdy dekorator to niezależny byt, który możesz wywołać bezpośrednio na obiekcie bazowym zawsze i nie potrzebujesz do tego więcej dekoratorów po drodze.

To:
  1. $video = new PropertyGeter(
  2. new ThumbnailFromVideoCuter(
  3. new ContentGeter(
  4. new FilePuter)));
  5.  

i to:
  1. $video = new ThumbnailFromVideoCuter(
  2. new PropertyGeter(
  3. new ContentGeter(
  4. new FilePuter)));
  5.  


Ma dać ten sam efekt, daje, zapewne nie bo ThumbnailFromVideoCuter() zależy pewnie od obiektu PropertyGeter(), skoro potrzebny był Ci obserwator.

Ten post edytował com 11.01.2017, 00:52:22
Go to the top of the page
+Quote Post
Omenomn
post 11.01.2017, 01:46:22
Post #52





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


Cytat
Wskaż mi gdzie framework ma coś nie udokumentowane i nie wiesz co uzyskasz jak wykonasz dany fragment jego kodu.

To trochę tak jakbyś z kota chciał zrobić mysz


Mówię o routingu. Dziwnie Cię zdziwiło, że są metody przypisane do konkretnej akcji z urla.

Cytat
Podsumowując, właściwości nie powinny wędrować miedzy dekoratorami, bo wtedy już to nie jest dekorator! Dekorujesz konkrety obiekt bazę która rozszerzasz, a nie budujesz nad obiektem bazy nowego obiektu do rozszerzeń. Każdy dekorator to niezależny byt, który możesz wywołać bezpośrednio na obiekcie bazowym zawsze i nie potrzebujesz do tego więcej dekoratorów po drodze.


Miedzy dokoratorami będę przekazywał obiekt, w którym będzie się znajdował kontent pliku plus inne atrybuty, które można modyfikować, a nie jak do tej pory sam kontent. Dlatego musiałem rozwiązać problem przekazywania właściwości, ale z obiektem będzie prościej o wiele.

Cytat
To:
  1. $video = new PropertyGeter(
  2. new ThumbnailFromVideoCuter(
  3. new ContentGeter(
  4. new FilePuter)));


i to:
  1. $video = new ThumbnailFromVideoCuter(
  2. new PropertyGeter(
  3. new ContentGeter(
  4. new FilePuter)));




Ma dać ten sam efekt, daje, zapewne nie bo ThumbnailFromVideoCuter() zależy pewnie od obiektu PropertyGeter(), skoro potrzebny był Ci obserwator.


Nieprawda, znajdź mi informację, że w dekoratorze kolejność dekoratorów ma nie mieć znaczenia.
Choćby zawsze musi istnieć końcowy dekorator, który nie przyjmuje wartości do konstrukora, więc jeżeli musi istnieć końcowy, to może istnieć początkowy i może istnieć ustalona kolejność.
Go to the top of the page
+Quote Post
daro0
post 11.01.2017, 09:40:58
Post #53





Grupa: Zarejestrowani
Postów: 88
Pomógł: 12
Dołączył: 17.09.2014
Skąd: Krasnystaw

Ostrzeżenie: (0%)
-----


Prawda jest taka, że gdybym miał się tak zastanawiać nad tym wszystkim to bym nigdy nie skończył w terminie żadnego projektu a wymagania są określone przez klienta. Owszem czasem trzeba coś dodać, coś nie było przewidziane, jednak na ogół nie jest to problemem. Tak na szybko (pierwsze co mi przychodzi na myśl). Zakładam że jest formularz typu Multipart/Formdata w widoku a w nim daje się jakiś opis w pole tekstowe, jest pole do wybierania obrazka do uploadu oraz opcja checkbox, czy ma być miniaturka czy też nie a rozmiary są określone w konfiguracji frameworka.

application/classes/Request.php

  1. <?php defined('SYSPATH') OR die('No direct script access.');
  2.  
  3. class Request extends Kohana_Request
  4. {
  5. public function files($key = NULL)
  6. {
  7. if ($key === NULL)
  8. {
  9. return $_FILES;
  10. }
  11. else
  12. {
  13. return Arr::path($_FILES, $key);
  14. }
  15. }
  16. }
  17.  


i metoda kontrolera

  1. public function action_upload()
  2. {
  3. if ($this->request->method() == HTTP_Request::POST)
  4. {
  5. if ($this->request->files('attachment'))
  6. {
  7. $config = Kohana::$config->load('app.uploads.images');
  8. $options = array(
  9. 'image' => array(
  10. 'width' => Arr::path($config, 'image.width'),
  11. 'height' => Arr::path($config, 'image.height'),
  12. ),
  13. 'thumbnail' => array(
  14. 'width' => Arr::path($config, 'thumbnail.width'),
  15. 'height' => Arr::path($config, 'thumbnail.height'),
  16. ),
  17. 'use_thumbnail' => $this->request->post('chk_use_thumbnail') ? TRUE : FALSE,
  18. );
  19.  
  20. $result = Uploader::factory('Image')
  21. ->options($options)
  22. ->data($this->request->files('attachment'))
  23. ->execute();
  24. }
  25. }
  26. // do something
  27. }


To jest tylko jedno z możliwych podejść. Tutaj to czy jest miniaturka czy nie to jest określone na podstawie tego co zwraca $_POST a ten helper musiałby na podstawie tego wykonywać pewne operacje. Zakładam użycie helperów Image oraz Upload z tego frameworka.

Nie wiem jak by to wyglądało w Laravelu a już tym bardziej gdyby pisać całkowicie od zera.

Ten post edytował daro0 11.01.2017, 09:51:16
Go to the top of the page
+Quote Post
Omenomn
post 11.01.2017, 11:32:25
Post #54





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


Jak się poświęci więcej czasu przy jednym projekcie na dobre rozwiązanie problemu, to później tego rozwiązania można używać w kolejnych, i czas wykonania skraca się o wiele.
Piszą o tym w książkach o wzorcach i dobrych praktykach.
Problem jest rozwiązany i działa meeega!!
Teraz mam bibliotekę rozszerzalną na miliony sposobów, gotową do użycia w innych projektach.
Go to the top of the page
+Quote Post
ohm
post 11.01.2017, 11:55:48
Post #55





Grupa: Zarejestrowani
Postów: 623
Pomógł: 144
Dołączył: 22.12.2010

Ostrzeżenie: (0%)
-----


Cytat(Omenomn @ 11.01.2017, 11:32:25 ) *
Teraz mam bibliotekę rozszerzalną na miliony sposobów, gotową do użycia w innych projektach.


Tylko pytanie czy inni też będą wiedzieli jak tę bibliotekę szybko i łatwo użyć?
Go to the top of the page
+Quote Post
nospor
post 11.01.2017, 12:08:06
Post #56





Grupa: Moderatorzy
Postów: 36 557
Pomógł: 6315
Dołączył: 27.12.2004




Cytat
Tylko pytanie czy inni też będą wiedzieli jak tę bibliotekę szybko i łatwo użyć?
Soryy, ale nie bede sobie "nieulatwial" pracy tylko dlatego ze ktos moze kiedys nie wiedziec jak tego uzyc... Ja tez mam wlasne liby w Symfony ktore generalizuje mi rozne rzeczy, np Grid, edycja, usuwanie, w sume caly CRUD. Na napisanie tego poswiecilem chwilke czasu ale teraz kazdy kolejny CRUD to 15 minut robotyi wiem ze wszystko bedzie dzialac tak samo.

Wracajac do twojego pytania:
Po pierwsze, skoro klasa byla uzywana w projekcie, to sa przyklady uzycia
Po drugie, zazwyczaj jak potrzeba pisze sie komentarz.


--------------------

"Myśl, myśl, myśl..." - Kubuś Puchatek || "Manual, manual, manual..." - Kubuś Programista
"Szukaj, szukaj, szukaj..." - Kubuś Odkrywca || "Debuguj, debuguj, debuguj..." - Kubuś Developer

Go to the top of the page
+Quote Post
Omenomn
post 11.01.2017, 12:17:16
Post #57





Grupa: Zarejestrowani
Postów: 77
Pomógł: 0
Dołączył: 4.02.2014

Ostrzeżenie: (20%)
X----


Zgadzam się z nospor
Go to the top of the page
+Quote Post
com
post 11.01.2017, 14:46:37
Post #58





Grupa: Zarejestrowani
Postów: 3 034
Pomógł: 366
Dołączył: 24.05.2012

Ostrzeżenie: (0%)
-----


Cytat
Mówię o routingu. Dziwnie Cię zdziwiło, że są metody przypisane do konkretnej akcji z urla.


Nie napisałem że coś w tym dziwnego, napisałem, że masz tu strategie o której ja i inni mówiliśmy.

Cytat
Nieprawda, znajdź mi informację, że w dekoratorze kolejność dekoratorów ma nie mieć znaczenia.
Choćby zawsze musi istnieć końcowy dekorator, który nie przyjmuje wartości do konstrukora, więc jeżeli musi istnieć końcowy, to może istnieć początkowy i może istnieć ustalona kolejność.


Wgl nie zrozumiałeś dekoratorów.

Jedyne co musi istnieć to klasa która rozszerzasz, ona ma jakaś funkcjonalność w Twoim przypadku bazą jest Upload. I kiedy podczas tego uploadu zależy Ci żeby powstała miniaturka, wiec dodajesz do istniejącego obiektu Uploadu zrób mi miniaturkę. Dlatego tworzysz dekorator, którego jedynym zadaniem jest zmienić obiekt bazowy tak żeby zamiast pełnego obrazu zwrócona została miniaturka w jego miejscu.
Dla innego route chcesz miniaturkę obrócona o 180 stopni. Wiec bierzesz klase Upload bierzesz dekorator Thumbnail i dekorator Rotate i masz miniaturkę i obrócony. Ale nie ma znaczenia czy najpierw obrócisz potem zmniejszysz czy na odwrót i tak i tak efekt zawsze jest taki sam i tak powinno być u Ciebie, a tak nie jest bo u Ciebie każda klasa zależy od innej. W przypadku prawdziwego dekoratora nadawane ograniczenia/zmiany na obiekcie są od siebie nie zależne, wiec mogę mięć: miniaturkę; miniaturkę i obrócony == obrócony i miniaturka; obrócony, a wszystko to bez jakiejkolwiek zmiany w kodzie. Twoje początkowe założenie było blednę, czyli:
Cytat
Choćby zawsze musi istnieć końcowy dekorator

Nie ma czegoś takiego jak początkowy czy końcowy dekorator, jest obiekt który dekorujesz i jeśli dekoratory maja ten sam interface co ten obiekt, to można je ze sobą składać tak jak było opisane w przykładach, ale tylko i wyłącznie wtedy.

Cytat
Soryy, ale nie bede sobie "nieulatwial" pracy tylko dlatego ze ktos moze kiedys nie wiedziec jak tego uzyc...

Tu wcale nie chodzi o nie ułatwianie pracy, bo po to zaproponowane zostało użycie wzorców, żeby te rozwiązanie było jak najbardziej elastyczne i można było wykorzystać je w wielu projektach, ale wzorce zostały zdefiniowane w taki sposób, żeby każdy kto sporzy na kod, znając je wie jaki będzie efekt. A kiedy kolega Omenomn po roku czy dwóch latach wróci do tego kodu coś zmienić, najpierw znów będzie musiał wdrożyć sam siebie jak to działa i czemu tak to zrobiłem wtedy a nie inaczej.

Przeczytaj jeszcze raz uważnie co tam zostało napisane
http://blogophp.com/2009/08/16/dekorator/#more-40
Najistotniejsze fragmenty
Cytat
// obiekty tej klasy beda dekorowane
class SimpleText extends Information

Cytat
Proszę zwrócić uwagę na fakt, iż gdy obiekt dekorowany jest tego samego typu co dekoratory jesteśmy w stanie ?dekorować? również dekoratory


obiekt dekorowany !== dekorator i nie możesz go nazwać dekoratorem końcowym.

Pomijając już sam fakt, że tak jak tam było:
new FirstLetter(new TextLength(new SimpleText()));
Dekoratory idą od środka w górę, a u Ciebie odnoszę wrażenie, że idziesz od początku w dół, przynajmniej tak wynikało z pierwszego opisu.

Trochę wracając jeszcze do tematu frameworka i jego roli, o czym mówiliśmy wcześniej to przykład od olx:


Ten post edytował com 11.01.2017, 19:27:12
Go to the top of the page
+Quote Post
solificati
post 11.01.2017, 15:19:06
Post #59





Grupa: Zarejestrowani
Postów: 26
Pomógł: 10
Dołączył: 17.03.2012

Ostrzeżenie: (0%)
-----


Cytat(Omenomn @ 11.01.2017, 02:46:22 ) *
Nieprawda, znajdź mi informację, że w dekoratorze kolejność dekoratorów ma nie mieć znaczenia.
Choćby zawsze musi istnieć końcowy dekorator, który nie przyjmuje wartości do konstrukora, więc jeżeli musi istnieć końcowy, to może istnieć początkowy i może istnieć ustalona kolejność.

Principle of least astonishment jak to się w kulturze OOP nazywa. Gdy kolejność ma znaczenie to wprowadzasz składnię a to się liczy conajmniej jako "zaskoczenie".

Precyzując, Dekorator implementuje ten sam interfejs, który implementuje obiekt który jest dekorowany. Żeby dekorator mógł korzystać z pól dodanych przez inny dekorator, musisz wprowadzić drugie drzewo dekoratorów bazujące na poszerzonym interface albo ich produkcie.

Ten post edytował solificati 11.01.2017, 15:34:27
Go to the top of the page
+Quote Post
daro0
post 11.01.2017, 16:42:08
Post #60





Grupa: Zarejestrowani
Postów: 88
Pomógł: 12
Dołączył: 17.09.2014
Skąd: Krasnystaw

Ostrzeżenie: (0%)
-----


Jeszcze rok albo dwa lata temu przy wcześniejszych projektach to też myślałem że to co wtedy pisałem jest super. Jakże się myliłem, bo teraz jak na to popatrzę to aż szlak trafia bo można było to napisać inaczej. Ale dalej. Weźmy np. nie uploader ale StaticServer

  1. class Controller_Image extends Controller
  2. {
  3.  
  4. public function action_serve()
  5. {
  6. $image = Image::factory(DOCROOT . '/test.jpg');
  7.  
  8. $size = $this->request->query('size');
  9. $rotate = $this->request->query('rotate');
  10. $sharp = $this->request->query('sharp');
  11. $quality = $this->request->query('quality');
  12.  
  13. if ($size)
  14. {
  15. $width = $image->width;
  16. $height = $image->height;
  17. $image->resize($width * $size / 100, $height * $size / 100);
  18. }
  19.  
  20. if ($rotate)
  21. {
  22. $image->rotate($rotate);
  23. }
  24.  
  25. if ($sharp)
  26. {
  27. $image->sharpen($sharp);
  28. }
  29.  
  30. if ($quality)
  31. {
  32. $image = $image->render('jpg', $quality);
  33. }
  34.  
  35. $this->response->headers('Cache-Control', 'max-age=3600, public');
  36. $this->response->headers('Content-Type', 'image/jpg');
  37. $this->response->body($image);
  38. }
  39.  
  40. }


I tak:

http://localhost/image/serve - wyświetla oryginalny obrazek JPG który wczyta
http://localhost/image/serve?size=50 - wyświetla obrazek w rozmiarach 50% oryginału
http://localhost/image/serve?size=50&sharp=100 - to samo ale wyostrzone
http://localhost/image/serve?quality=10 - jakość JPG 10%
http://localhost/image/serve?rotate=90 - obraza o 90 stopni w prawo

Domyślnie metoda __toString() wywołuje na render() w tym module.

I teraz jest pytanie, co w takim przypadku daje zastosowanie dekoratora (bo też można by to zrobić) vs. to podejście jakie jest tu?
Go to the top of the page
+Quote Post

10 Stron V  < 1 2 3 4 5 > » 
Closed TopicStart new topic
1 Użytkowników czyta ten temat (1 Gości i 0 Anonimowych użytkowników)
0 Zarejestrowanych:

 



RSS Wersja Lo-Fi Aktualny czas: 17.06.2025 - 21:36