Wiele parametrów konstruktora czy klasa abstrakcyjna?

Wiele parametrów konstruktora czy klasa abstrakcyjna?
Shalom
  • Rejestracja:około 21 lat
  • Ostatnio:prawie 3 lata
  • Lokalizacja:Space: the final frontier
  • Postów:26433
0

Refaktoruje ostatnio bardzo dużo słabego kodu w pracy i w trakcie usuwania duplikacji zacząłem się zastanawiać nad pewną kwestią. Załóżmy, że wydzielam sobie kod pewnego panelu GUI. Panel jest używany w wielu miejscach i jest generalnie identyczny, ale różni się:

  • labelkami
  • tooltipami
  • akcjami jak ktoś cośtam kliknie na przykład

Gdyby tych parametrów było mało i gdyby nie było tam "akcji" to pewnie bez zastanowienia wrzucałbym je przez konstruktor. Liczbę parametrów zawsze można ograniczyć jakimś DTO ale to taki sobie pomysł bo to DTO nigdzie nie byłoby używane a jedynie tworzone w miejscu tworzenia panelu z parametrów znanych w chwili kompilacji. Więc dość słabo. Dodatkowo "akcje" trzeba by wrzucać jako jakieś lambdy albo funktory.
Dodatkowo część tych parametrów może być zostawiona jako domyślna, co mocno komplikuje opcje z konstruktorem, bo albo mamy mother of all constructors a potem kupę nulli jako parametry albo mamy milion konstruktorów (mało możliwe bo niektóre parametry są tego samego typu ;) ).

W związku z tym pomyślałem że można to zrobić z zupełnie innej strony. Zrobić klasę abstrakcyjną z metodami w stylu getXYZTooltip() a wymagane akcje zrobić jako metody abstrakcyjne. Wtedy tworząc obiekt musimy zaimplementować wymagane metody i ewentualnie przeładować te gdzie nie chcemy używać opcji domyślnych. Tylko że to rozwiązanie wydaje mi się trochę dziwne, bo jednak tworzymy nową klasę (choćby i anonimową) podczas gdy w rzeczywistości te klasy różnią się właściwie tylko parametrami (szczególnie jeśli uznamy lambdy za parametry).

Co o tym myślicie?
@somekind @Koziołek @Krolik @niezdecydowany @karolinaa @msm @winerfresh @stryku @Patryk27 @katelx @WhiteLightning @datdata @spartanPAGE @Wizzie @Azarien @Satirev @MarekR22 @Afish @panryz @Wibowit @azalut i więcej mi się nie chce wymieniać, ale niech się nikt nie czuje pominięty! (kolejność losowa!)


"Nie brookliński most, ale przemienić w jasny, nowy dzień najsmutniejszą noc - to jest dopiero coś!"
edytowany 1x, ostatnio: Shalom
Zobacz pozostałe 12 komentarzy
azalut
@Shalom ja bym chetnie taka funkcje chciał :P czasem coś szukam o kims na forum bo np pamietam ze gdzies sie udzielil i potrzebuje tego tematu i męczarnia jest ;)
panryz
ja ostatnio przejrzałem moje stare posty :D Laik laik laik ale teraz mam świadomość jakim userem byłem w oczach niektórych ja zadawałem takie pytania :D
panryz
aaa w ogóle @Shalom dlaczego ja się tutaj znalazłem w tym gronie? Za wiele wiedzy tutaj nie zostawiam (mało pytań o androida) jedyne co to mam na koncie bana (i to cofniętego) za podcinanie skrzydeł "nowicjuszom" :D
Shalom
@panryz ot wybrałem top trolli :P
msm
O, ktoś mnie woła, i to dwa razy w jednym wątku. @azalut - jeśli masz jakieś wymarzone zapytanie/data mining na bazie 4p to powiedz, mogę coś wykonać :P. Wszystkie Twoje głupie posty sprzed 2 lat wyjdą na jaw.
Wibowit
  • Rejestracja:prawie 20 lat
  • Ostatnio:około 18 godzin
9

Pokaż kod :P


"Programs must be written for people to read, and only incidentally for machines to execute." - Abelson & Sussman, SICP, preface to the first edition
"Ci, co najbardziej pragną planować życie społeczne, gdyby im na to pozwolić, staliby się w najwyższym stopniu niebezpieczni i nietolerancyjni wobec planów życiowych innych ludzi. Często, tchnącego dobrocią i oddanego jakiejś sprawie idealistę, dzieli od fanatyka tylko mały krok."
Demokracja jest fajna, dopóki wygrywa twoja ulubiona partia.
mychal
  • Rejestracja:ponad 15 lat
  • Ostatnio:ponad 8 lat
  • Lokalizacja:Przedmonitorze Górne
4

Może po prostu builder?


I fart u die.
azalut
  • Rejestracja:około 12 lat
  • Ostatnio:ponad rok
  • Postów:1129
1

w tym panelu się layout zmienia? czy wszystko zostaje tak samo tylko "napisowe elementy" sie zmieniają?

w panelu zmieniają się też np buttony? bo jak przeczytałem to pomyslalem, że jeśli występowałby taki związek między tymi elementami, że np: jest buton, każdy buton ma label, kazdy label ma tooltip i jeszcze action na kliknięcie to możnaby stworzyć obiekt upakowujący te pare obiektów i takie zestawy dodawać przez konstruktor i zrobić jakiś limit (nie wiem czy to ta sama idea o której mówisz pisząc o DTO). Ale to wtedy jeśli cały layout albo chociaż takie "paczki" obiektów sie zmieniaja na tym twoim panelu

Co do twojego pomysłu, mówisz tylko o akcjach na kliknięcie? czy chodzi o taką defaultową klase dla panelu/elementów gui i ew. reimplementacji tego co akurat potrzeba? (tzn np getXYZTooltip() zmieniasz napis tipa) bo nie do końca łapie

edytowany 2x, ostatnio: azalut
niezdecydowany
niezdecydowany
  • Rejestracja:ponad 12 lat
  • Ostatnio:ponad 9 lat
  • Lokalizacja:Bieszczady
3

Wujek Bloch faktycznie, powie Builder :) ale ciężko w ogóle powiedzieć, bo jeżeli masz już zdefiniowane że ta klasa ma 5 tooltipów (

Kopiuj
getXYZTooltip() 

) i one są zawsze wymagane, to raczej ciężko zrobić z tego "pikny" kod :D Zamiast tej klasy abstrakcyjnej, ciała tych metod (które wcześniej chciałeś po prostu nadpisać) lepiej chyba podać lambdą - nie musisz za każdym razem robić nowej anonimowej klasy (+10000 do wydajności :)) a i lepiej wygląda (i te akcje mogą być faktycznie podawane builderem)

Kopiuj

setXXTooltip(p->p.costamZrob()).setYYTooltip(p->p.sendWiadomoscDoGdziestam).setZZZTooltip(p::costam);

A tak serio to napisałem tylko po to żeby poczuć się inteligientny :D:D:D w końcu umiem tylko klepać formy :D:D:D:D:D:D


"Perhaps surprisingly, concurrent programming isn’t so much about threads or
locks, any more than civil engineering is about rivets and I-beams."
edytowany 2x, ostatnio: niezdecydowany
azalut
:DD końcówka best
niezdecydowany
niezdecydowany
#wiejskiglupek
Shalom
  • Rejestracja:około 21 lat
  • Ostatnio:prawie 3 lata
  • Lokalizacja:Space: the final frontier
  • Postów:26433
0

@mychal builder to faktycznie jest klasyczne rozwiązanie jeśli chodzi o problem z konstruktorem, niemniej nadal będę miał gigantyczną "wiązankę" tworzącą taki panel. A mam okienko gdzie jest ich kilka obok siebie ;) Rozwiązanie z klasą abstrakcyjną pozwala wyrzucić ten kod do osobnej klasy i na oko wygląda trochę czytelniej.

@Wibowit @datdata akurat kod nie ma tu specjalnie wiele do rzeczy. Chodzi mi raczej o taką teoretyczną rozkminę ;)

@azalut w panelu nie zmieniają się komponenty, tzn masz tam jakieś pole tekstowe, jakieś buttony etc i to jest stałe. Zmieniają się labelki, tooltipy i akcje. Jeśli chodzi o to nadpisywanie to wyobraź sobie że np. metoda getTooltipForTextFieldX() defaultowo zwraca pustego stringa a jak w danym miejscu chcesz mieć tooltip to ja przeładowujesz. Trochę tak jak np. javowe klasy XYZAdapter dla ActionListenerów.


"Nie brookliński most, ale przemienić w jasny, nowy dzień najsmutniejszą noc - to jest dopiero coś!"
edytowany 1x, ostatnio: Shalom
Wibowit
  • Rejestracja:prawie 20 lat
  • Ostatnio:około 18 godzin
2

A są jakieś powielające się zbiory własności? Jeśli tak, to możesz zrobić metodę klonującą w budowniczym oraz metody dodające zachowania, np metoda typu:

Kopiuj
PanelBuilder addYellowTooltips() {
  tooltipsColor = Yellow;
  return this;
}

Później możesz mieć konstrukcje tego typu:

Kopiuj
PanelBuilder genericBuilder = new PanelBuilder().setA(blabla).setB(bleble);
PanelBuilder passwordBuilder = genericBuilder.clone().setTitle("Password reset").showLabel(Labels.PasswordLabel);

Jeśli chodzi o dowolne składanie akcji to możesz zrobić interfejs ze wszystkimi wspólnymi akcjami. Do tego klasę, która ma puste lub domyślne implementacje każdej akcji. Następnie możesz użyć wzorca https://pl.wikipedia.org/wiki/%C5%81a%C5%84cuch_zobowi%C4%85za%C5%84_(wzorzec_projektowy) (chain of responsibility) do zaimplementowania składania zachowań. Kod mógłby być taki:

Kopiuj
interface Actions {
  void actionA();
  void actionB();
  void actionC();
}

class ActionsAdapter {
  void actionA() {}
  void actionB() {}
  void actionC() {}
}

class ActionAdapterChain extends ActionsAdapter {
  final ActionsAdapter previous;
  // konstruktor

 // metody delegujące do previous
}

class PanelBuilder {
  Actions actions = new ActionsAdapter();
  ...
  PanelBuilder blinkOnClick() {
    Actions oldActions = actions;
    actions = new ActionAdapterChain(actions) {
      @Override void actionA() { 
        oldActions.actionA(); // albo można olać tę linijkę
        blink(); 
      }
    }
    return this;
  }
  ...
  PanelBuilder genericBuilder = ...
  PanelBuilder blinkingBuilder = genericBuilder.clone().blinkOnClick();
}

"Programs must be written for people to read, and only incidentally for machines to execute." - Abelson & Sussman, SICP, preface to the first edition
"Ci, co najbardziej pragną planować życie społeczne, gdyby im na to pozwolić, staliby się w najwyższym stopniu niebezpieczni i nietolerancyjni wobec planów życiowych innych ludzi. Często, tchnącego dobrocią i oddanego jakiejś sprawie idealistę, dzieli od fanatyka tylko mały krok."
Demokracja jest fajna, dopóki wygrywa twoja ulubiona partia.
edytowany 2x, ostatnio: Wibowit
azalut
  • Rejestracja:około 12 lat
  • Ostatnio:ponad rok
  • Postów:1129
0

@Shalom już chyba rozumiem, wydaje się dobre ale ja to widze jakos tak:
zrobić zwykłą klasę, nie abstrakcyjna i defaulotowo zrobić tak jak mowisz, na przyklad.. hm.. mieć pare pól z defaultowymi akcjami. Dla tipa bedzie to pusty String, a dla akcji na klikniecie bedzie do jakis @FunctionalInterface
I teraz - zrobisz obiekt panelu i wszystko jest defaultowo, a jesli chcesz zmienic zachowanie np dla klikniecia butonu to robisz dla każdego pola setter i wstawiasz nowego stringa albo nową funkcję

(jesli dobrze cie rozumiem) to wyprodukowaloby troche mniej kodu niz abstrakcyjna anonimowa klasa i implementowanie tego co chcesz, szczegolnie, ze lambdy mozesz tam wrzucic a to "jednolinijkowce"
Jesli takich nie-defaultowych wymagan byloby nie duzo to kod tez nie bylby jakis rozwlekly
ma to sens jakiś? bo to nagle mi przyszlo do glowy :D

datdata
  • Rejestracja:prawie 11 lat
  • Ostatnio:około 7 lat
  • Postów:957
0

Jeszcze tego w taki sposób nie robiłem, ale czy nie jako pomoc w tego typu sytuacjach nie powstało to:

https://docs.oracle.com/javase/tutorial/java/IandI/defaultmethods.html


"A human being should be able to change a diaper, plan an invasion, butcher a hog, conn a ship, design a building, write a sonnet, balance accounts, build a wall, set a bone, comfort the dying, take orders, give orders, cooperate, act alone, solve equations, analyze a new problem, pitch manure, program a computer, cook a tasty meal, fight efficiently, die gallantly. Specialization is for insects." Robert Heinlein.
Zobacz pozostały 1 komentarz
datdata
@niezdecydowany jutro spojrzę na problem jeszcze raz, bo to może być pomysł po browarze ;)
niezdecydowany
niezdecydowany
problem jest taki, że to co chciałeś zrobić jest naturalne - ale nie można wsadzać logiki do interfaców, według Oracla, zostało to stworzone (default methods) z myślą o nowych metodach w starym API, możesz dzisiaj co Collection wsadzić metodę getDupaAsList() i nikt się nie obrazi, bo LinkedLista nie musi tego implementować. Ekstremalnie możesz tam wsadzać jakieś zachowanie które nazwałbym stateless, dajmy na to że masz metode processElement(T elemtn)
niezdecydowany
niezdecydowany
To metoda domyślna może posiadać zachowanie, dajmy na to default processListOfElements(List<T>) - bo np: interface jest generyczny, w tedy ta metoda jest uzależniona od tej abstrakcyjnej, także nie wprowadza żądnego stanu, jest to w miarę bezpieczne - z tego np:, korzysta się w Stremach w javie 8 - dzięki temu nie rozyebali 100pierdyliardów interfaców, tylko możesz na każdej liście zrobić .stream();
datdata
Ok, wstępnie rozumiem. My bad.
datdata
Oka, rozumiem. My bad.
MA
  • Rejestracja:około 10 lat
  • Ostatnio:około 6 godzin
  • Lokalizacja:Poznań
  • Postów:216
0

Jak już taka rozkminka to może FluentAPI? Domyślnie masz jeden domyślny konstruktor, który ustawia wszystko na wartość zerową/pustą, następnie piszesz sobie jakieś extension functions, żeby działało to tak:

Potrzebujesz okienko z jednym tooltipem i jedną akcją:

Kopiuj
      BaseWindow.Create().WithTooltip("id", "text").WithButton("buttonID").WithAction("componenID", () => { /* ... */ });

Żeby nie trzeba było powtarzać kodu do tworzenia tych samych "komponentów" w różnych okienkach, może i coś takiego:

Kopiuj
      var sharedComponents =  ComponentsCollection.Create().WithTooltip("id", "text").WithButton("buttonID").WithAction("componenID", () => { /* ... */ });
      var customWindow1 = BaseWindow.Create().WithComponents(sharedComponents).WithButton("buttonID2").WithAction("buttonID2", () => { /* ... */});
      var customWindow2 = BaseWindow.Create().WithComponents(sharedComponents).WithTooltip("ID", "TEXT2");

Nie wiem czy to dobry pomysł :D

Shalom
  • Rejestracja:około 21 lat
  • Ostatnio:prawie 3 lata
  • Lokalizacja:Space: the final frontier
  • Postów:26433
0

@Wibowit właściwości się nie powtarzają w zasadzie nigdy. Akcje zresztą też nie, bo "akcje" to są zwykle wywołania prezentera/kontrolera. Może krótki opis o jaką sytuację mi chodzi:

Założmy że mam sobie panel który ma pole tekstowe, guzik który robi "browse" i pozwala wybrać plik z dysku oraz guzik "process". Są tam jeszcze jakieśtam labelki, tooltipy itd. I teraz identyczny panel jest używany w kilku miejscach w aplikacji, ale do zupełnie innych "celów" z punktu widzenia biznesowego. Tzn dotyczy zupełnie innego widoku a "process" wywołuje zupełnie inne akcje kontrolera. Więc robienie listy wszystkich akcji albo takiego generycznego buildera odpada.

Zwykły builder jak najbardziej by sie nadał, ale jego słaba strona to fakt że jak mam widok gdzie jest takich paneli np. 5 to nagle się tam robi 100 linii kodu tworzenia tych paneli z odpowiednich parametrów ;]

@azalut jasne że można i tak, ale to sie niczym nie rożni od buildera ;) Kodu technicznie byłoby mniej, ale byłby upchany w jednym miejscu ;)


"Nie brookliński most, ale przemienić w jasny, nowy dzień najsmutniejszą noc - to jest dopiero coś!"
edytowany 1x, ostatnio: Shalom
MarekR22
Moderator C/C++
  • Rejestracja:około 17 lat
  • Ostatnio:3 minuty
0

Jaki framework? Takie rzeczy powinny/mogą być rozwiązane już na poziomie użytego framework (nie ma nic gorszego jak usilne walczenie z frameworkiem).
Przykładowo w Qt jest QAction, które robi dokładnie to co potrzebujesz.
Do jednego UI podłącza się QAction, które dostarcza tytuł ikonkę i zachowanie, a w razie potrzeby stan UI (czy element powinien być checkable, enabled itp).


Jeśli chcesz pomocy, NIE pisz na priva, ale zadaj dobre pytanie na forum.
Zobacz pozostałe 2 komentarze
Shalom
No i teraz za karę muszę takie cuda robić :P Ty się śmiejesz a wyobraź sobie że aplikacja do przeglądania danych z ATV w control center miała UI w swingu :P
azalut
rozdupcył i kare dostał
Shalom
@niezdecydowany @azalut jak chcecie zobaczyć nierozdupcone (jeszcze :P) łaziki to Tegoroczne europejskie zawod... ;)
niezdecydowany
niezdecydowany
no dobra, zajarzyłem, dałem Ci lajka ^^ a co jedziesz do tego grodu Liroya ?
Shalom
Za daleko ;]
panryz
  • Rejestracja:prawie 17 lat
  • Ostatnio:około 8 godzin
0

Generalnie tak:
ja jakimś mega JAVAMASTER nie jestem, aale pierwsze o czym pomyślałem to wspomniany Builder

edytowany 1x, ostatnio: panryz
Zobacz pozostały 1 komentarz
panryz
Czyli NPE jest porządany, tak? :D
panryz
A dobra kumam, o co mu chodziło z tymi nullami w konstruktorze. Przyjdę jutro jak się wyśpię.
azalut
jak wytrzeźwiejesz? haha
niezdecydowany
niezdecydowany
panowie, 30 strona efektywnej javy, polecam :D
panryz
@niezdecydowany to się zgadza 30 strona effective java :D
KA
KA
  • Rejestracja:prawie 12 lat
  • Ostatnio:prawie 5 lat
  • Lokalizacja:Warszawa
  • Postów:1683
0

oddaję głos na klasę abstrakcyjną. builder w javie to trochę boilercode taki a lombok i te step builder generatory pluginy nawet nie umieją wygenerować step buildera z opcjonalnymi polami. parametry przekazywane przez klasę anonimową do dużego konstruktora też są dla mnie spoko. zajmują sporo linii ( @Override ) , ale chociaż wszystko widać jak na dłoni.


PROGRAMY NA ZAMÓWIENIE, ZALICZENIA STUDENCKIE, KONFIGURACJA SERWERÓW, SYSTEMÓW I BAZ DANYCH, STRONY INTERNETOWE, POMOC W PROGRAMOWANIU, POPRAWIENIE I OPTYMALIZACJA APLIKACJI
JAVA, C++, LINUX, WWW, SQL, PYTHON
POSIADAM KOMERCYJNE DOŚWIADCZENIE
TANIO, SZYBKO I PORZĄDNIE
Z KOMENTARZAMI OBJAŚNIAJĄCYMI KOD
PISZ NA PRYWATNĄ WIADOMOŚĆ
CENY JUŻ OD 49,99ZŁ ZA PROGRAM
ZAJMIJ SIĘ TYM CO CIĘ NAPRAWDĘ INTERESUJE!
Koziołek
Moderator
  • Rejestracja:prawie 18 lat
  • Ostatnio:około 2 miesiące
  • Lokalizacja:Stacktrace
  • Postów:6821
0

Jak widzę nie mogę chodzić spać o ludzkich porach, bo pomijam ciekawe dyskusje :)

Miałem podobny problem w jednym z projektów tyle tylko, że zamiast przepisywać coś co już istnieje rzeźbiłem od zera. Problem podzieliłem na dwa obszary:

  1. tooltipy i labelki - to jest tak naprawdę jeden i ten sam problem pobierania danych, ale w różnych ujęciach.
  2. akcje - ten problem jest "bliżej" kodu.

Problem 1. można łatwo rozwiązać poprzez użycie "magii" w postaci (można to zrobić ładniej) labelService.getLabel(getClass().getCanonicalName() + ".myLabel1") i następnie w pliku properties masz litanię opisów. Wystarczy wstrzyknąć serwis. Zaleta - jest proste (prościej się nie da), wada - jeżeli w ramach jednej klasy masz dwa obiekty z różnymi napisami to musisz jeszcze rozszerzyć o jakiś "name" obiektu. Całość można ogarnąć jak napisał @azalut za pomocą interfejsów i default metod, tak by w punkcie gdzie używasz wystarczyło napisać getLabel("myLabel") i gotowe.

Problem 2. rozwiązałem przez klasę abstrakcyjną, która dostarczała szablon GUI oraz metody abstrakcyjne do tworzenia akcji. Zaletą jest znowuż prostota i duża intuicyjność rozwiązania. Wadą, chyba najpoważniejszą, jest dość trudna implementacja dla dynamicznych struktur typu tabele o zmiennej ilości kolumn. Trzeba wtedy nadpisywać część zachowania bądź tworzyć metody abstrakcyjne, które będą dostarczały całe bloki GUI.


Sięgam tam, gdzie wzrok nie sięga… a tam NullPointerException
krzysiek050
  • Rejestracja:ponad 12 lat
  • Ostatnio:około 4 lata
  • Postów:1272
0

A może połączenie buildera i protypu? Najpierw inicjujujesz builder jakimś już zbudowanym panelem, a potem tylko budujesz nadpisując właściwości prototypu. Nie robiłbym też specjalnego rozróżniania na akcje/tooltipy/buttony. W większości języków przekazujemy je do metod tak samo i z punktu widzenia budowania jest tym samym, czyli właściwością panelu.

Shalom
  • Rejestracja:około 21 lat
  • Ostatnio:prawie 3 lata
  • Lokalizacja:Space: the final frontier
  • Postów:26433
0

@Koziołek
ad.1. Tak jak pisałem wcześniej, te labelki i tooltipy się nie powtarzają w zasadzie więc taki generyczny serwis który by je serwował wydaje się taki-sobie. Szczególnie że nie muszę sie tu martwić o jakąś lokalizację czy internacjonalizację - w takiej sytuacji musiałbym tak czy siak eksternalizować te teksty i ładować dynamicznie i wtedy opcja z pobieraniem na podstawie ID miałaby sens.
ad.2. Tutaj akurat problem nie jest aż tak złożony bo akurat to są proste komponenty.


"Nie brookliński most, ale przemienić w jasny, nowy dzień najsmutniejszą noc - to jest dopiero coś!"
Koziołek
Moderator
  • Rejestracja:prawie 18 lat
  • Ostatnio:około 2 miesiące
  • Lokalizacja:Stacktrace
  • Postów:6821
0

@Shalom, eksternalizuj stringi gdzie się tylko da. Nie ma nic gorszego niż litrówka, której poprawienie wymaga rebuildu całej apki ;) cała magia tego serwisu polega na tym, że ostro oddzielasz dane (treść napisów) od apki.


Sięgam tam, gdzie wzrok nie sięga… a tam NullPointerException
Shalom
Nie ma nic gorszego niż ten kod który refaktoruje :P Każda klasa na 5+k linii kodu, oczywiście mvc w wydaniu 3w1, GUI z netbeansowego generatora i do tego wszechobecny copy-paste. Literówka w labelce to najmniejszy problem :D
Koziołek
Tyle tylko, ze to są rzeczy, które widać. W dodatku dość proste do ogarnięcia i można się elegancko wdrożyć w proces dla danej kontrolki zaczynając od tak prozaicznej rzeczy.
WhiteLightning
  • Rejestracja:prawie 14 lat
  • Ostatnio:około 12 godzin
  • Postów:3169
0

Koziołek ma racje- co się da wywalić do plików konfiguracyjnych. Nie znam szczegolow, ile tam jest tych akcji, jako dokladnie wyglada, ale mozna tez zrobic w apce aby dalo sie wybierac akcje na podstawie configu (taki actionSelector).

AF
  • Rejestracja:prawie 18 lat
  • Ostatnio:20 dni
1

We wzorcu builder zrobiłbym metody tworzące zdefiniowane z góry ogólne panele, które potem klonowałbym i rozszerzał o pozostałe elementy. Składanie każdego panelu przez wywołanie wszystkich metod jest słabe, bo co zrobisz, gdy trzeba będzie zmodyfikować jakąś głupotę we wszystkich panelach? Ogólnie rozwiązanie @Wibowit wydaje się całkiem niezłe na początek, ale bez znajomości całego kodu jest to wróżenie z fusów.
@Koziołek dobrze prawi o plikach konfiguracyjnych z etykietami. Na początku wystarczy hardkodowanie identyfikatorów, potem można pomyśleć nad jakąś sprytną refleksją.
Jeżeli chodzi o akcje, to zależy od ich wielkości - jeżeli jest to jedna linijka, to lambda przejdzie, ale jak ma być to coś grubszego, to wzorzec strategia + jakiś pipelining. Jeżeli akcje też są podobne, to można i tutaj użyć buildera.

niezdecydowany
niezdecydowany
ogarnij... @Shalom chce poprawić czytelność, a Wy z refleksją, to już lepiej niech to zostawi w pizdu tak jak jest, zduplikowane - łatwiej to potem zrozumieć.
Koziołek
@niezdecydowany, dobrze ukryta refleksja jest ok w takim miejscu. Patrz mój przykład.
niezdecydowany
niezdecydowany
śmierdzi mi takie kombinowanie, "metaprogramowanie" jest dobre w ruby w projektach typu "kolejny startup" a nie w bizneso świnkach, Wy tam guavy użyć nie możecie ale refleksja jest ok ? niektóre rzeczy, tak jak unsafe powinny być wyyebane z automatu.
AF
@niezdecydowany Nie zgadzam się, że to jest nieczytelne. Może być mniej zrozumiałe na początku, ale moim zdaniem koszt i tak jest do przyjęcia. Oczywiście to zależy od efektu finalnego, jeżeli trzeba będzie robić jakieś wygibasy refleksją, żeby wyciągnąć dane ze zbudowanego obiektu, to wtedy w istocie lepiej zostawić hardkodowane identyfikatory.
niezdecydowany
niezdecydowany
Ty się tam akurat możesz nie zgadzać ^^
Shalom
  • Rejestracja:około 21 lat
  • Ostatnio:prawie 3 lata
  • Lokalizacja:Space: the final frontier
  • Postów:26433
0

@Koziołek @WhiteLightning ja nie mówię że to jest zły pomysł, ale wolę robić takie zmiany inkrementalnie, tzn najpierw podzielić cały ten kod po ludzku na MVP, potem usunąć duplikacje i powydzielać wspólne elementy, potem zrobić jakiś strukturalny refaktoring (podzielić wielkie klocki na małe metody, powydzielać klasy etc) a dopiero potem się brać za takie szczegóły jak wyrzucenie stringów do osobnej konfiguracji ;)


"Nie brookliński most, ale przemienić w jasny, nowy dzień najsmutniejszą noc - to jest dopiero coś!"
Koziołek
zatrudnij jakąś cycatą do pracy z tymi stringami ;) a na serio to może być dobry start point ;)
somekind
Chyba ciapatą :P
Koziołek
Poprawianie kodu za pomocą hindusów... nope, nope, nope.....
WhiteLightning
To jeszcze pytanie jak testy projektu, bo jesli sa i dzialaja to i tak jest niezle:)
katelx
  • Rejestracja:prawie 10 lat
  • Ostatnio:4 miesiące
  • Lokalizacja:Hong Kong
2

@Shalom! ktos ci sie na konto wlamal i pytania zadaje ;)

ja bym szla w kierunku tych klas abstrakcyjnych, tak zeby akcje byly metodami a caly smietnik zwiazany z labelami, tooltipami etc upakowac w cos slownikopodobnego (skoro nie chcesz miec zewnetrznych zasobow), tzn idkontrolki:wartosc i trzymac jako jednego gettera.
oczywiscie wszystko opakowac w jakas fabryke, w koncu java ;)

Kliknij, aby dodać treść...

Pomoc 1.18.8

Typografia

Edytor obsługuje składnie Markdown, w której pojedynczy akcent *kursywa* oraz _kursywa_ to pochylenie. Z kolei podwójny akcent **pogrubienie** oraz __pogrubienie__ to pogrubienie. Dodanie znaczników ~~strike~~ to przekreślenie.

Możesz dodać formatowanie komendami , , oraz .

Ponieważ dekoracja podkreślenia jest przeznaczona na linki, markdown nie zawiera specjalnej składni dla podkreślenia. Dlatego by dodać podkreślenie, użyj <u>underline</u>.

Komendy formatujące reagują na skróty klawiszowe: Ctrl+B, Ctrl+I, Ctrl+U oraz Ctrl+S.

Linki

By dodać link w edytorze użyj komendy lub użyj składni [title](link). URL umieszczony w linku lub nawet URL umieszczony bezpośrednio w tekście będzie aktywny i klikalny.

Jeżeli chcesz, możesz samodzielnie dodać link: <a href="link">title</a>.

Wewnętrzne odnośniki

Możesz umieścić odnośnik do wewnętrznej podstrony, używając następującej składni: [[Delphi/Kompendium]] lub [[Delphi/Kompendium|kliknij, aby przejść do kompendium]]. Odnośniki mogą prowadzić do Forum 4programmers.net lub np. do Kompendium.

Wspomnienia użytkowników

By wspomnieć użytkownika forum, wpisz w formularzu znak @. Zobaczysz okienko samouzupełniające nazwy użytkowników. Samouzupełnienie dobierze odpowiedni format wspomnienia, zależnie od tego czy w nazwie użytkownika znajduje się spacja.

Znaczniki HTML

Dozwolone jest używanie niektórych znaczników HTML: <a>, <b>, <i>, <kbd>, <del>, <strong>, <dfn>, <pre>, <blockquote>, <hr/>, <sub>, <sup> oraz <img/>.

Skróty klawiszowe

Dodaj kombinację klawiszy komendą notacji klawiszy lub skrótem klawiszowym Alt+K.

Reprezentuj kombinacje klawiszowe używając taga <kbd>. Oddziel od siebie klawisze znakiem plus, np <kbd>Alt+Tab</kbd>.

Indeks górny oraz dolny

Przykład: wpisując H<sub>2</sub>O i m<sup>2</sup> otrzymasz: H2O i m2.

Składnia Tex

By precyzyjnie wyrazić działanie matematyczne, użyj składni Tex.

<tex>arcctg(x) = argtan(\frac{1}{x}) = arcsin(\frac{1}{\sqrt{1+x^2}})</tex>

Kod źródłowy

Krótkie fragmenty kodu

Wszelkie jednolinijkowe instrukcje języka programowania powinny być zawarte pomiędzy obróconymi apostrofami: `kod instrukcji` lub ``console.log(`string`);``.

Kod wielolinijkowy

Dodaj fragment kodu komendą . Fragmenty kodu zajmujące całą lub więcej linijek powinny być umieszczone w wielolinijkowym fragmencie kodu. Znaczniki ``` lub ~~~ umożliwiają kolorowanie różnych języków programowania. Możemy nadać nazwę języka programowania używając auto-uzupełnienia, kod został pokolorowany używając konkretnych ustawień kolorowania składni:

```javascript
document.write('Hello World');
```

Możesz zaznaczyć również już wklejony kod w edytorze, i użyć komendy  by zamienić go w kod. Użyj kombinacji Ctrl+`, by dodać fragment kodu bez oznaczników języka.

Tabelki

Dodaj przykładową tabelkę używając komendy . Przykładowa tabelka składa się z dwóch kolumn, nagłówka i jednego wiersza.

Wygeneruj tabelkę na podstawie szablonu. Oddziel komórki separatorem ; lub |, a następnie zaznacz szablonu.

nazwisko;dziedzina;odkrycie
Pitagoras;mathematics;Pythagorean Theorem
Albert Einstein;physics;General Relativity
Marie Curie, Pierre Curie;chemistry;Radium, Polonium

Użyj komendy by zamienić zaznaczony szablon na tabelkę Markdown.

Lista uporządkowana i nieuporządkowana

Możliwe jest tworzenie listy numerowanych oraz wypunktowanych. Wystarczy, że pierwszym znakiem linii będzie * lub - dla listy nieuporządkowanej oraz 1. dla listy uporządkowanej.

Użyj komendy by dodać listę uporządkowaną.

1. Lista numerowana
2. Lista numerowana

Użyj komendy by dodać listę nieuporządkowaną.

* Lista wypunktowana
* Lista wypunktowana
** Lista wypunktowana (drugi poziom)

Składnia Markdown

Edytor obsługuje składnię Markdown, która składa się ze znaków specjalnych. Dostępne komendy, jak formatowanie , dodanie tabelki lub fragmentu kodu są w pewnym sensie świadome otaczającej jej składni, i postarają się unikać uszkodzenia jej.

Dla przykładu, używając tylko dostępnych komend, nie możemy dodać formatowania pogrubienia do kodu wielolinijkowego, albo dodać listy do tabelki - mogłoby to doprowadzić do uszkodzenia składni.

W pewnych odosobnionych przypadkach brak nowej linii przed elementami markdown również mógłby uszkodzić składnie, dlatego edytor dodaje brakujące nowe linie. Dla przykładu, dodanie formatowania pochylenia zaraz po tabelce, mogłoby zostać błędne zinterpretowane, więc edytor doda oddzielającą nową linię pomiędzy tabelką, a pochyleniem.

Skróty klawiszowe

Skróty formatujące, kiedy w edytorze znajduje się pojedynczy kursor, wstawiają sformatowany tekst przykładowy. Jeśli w edytorze znajduje się zaznaczenie (słowo, linijka, paragraf), wtedy zaznaczenie zostaje sformatowane.

  • Ctrl+B - dodaj pogrubienie lub pogrub zaznaczenie
  • Ctrl+I - dodaj pochylenie lub pochyl zaznaczenie
  • Ctrl+U - dodaj podkreślenie lub podkreśl zaznaczenie
  • Ctrl+S - dodaj przekreślenie lub przekreśl zaznaczenie

Notacja Klawiszy

  • Alt+K - dodaj notację klawiszy

Fragment kodu bez oznacznika

  • Alt+C - dodaj pusty fragment kodu

Skróty operujące na kodzie i linijkach:

  • Alt+L - zaznaczenie całej linii
  • Alt+, Alt+ - przeniesienie linijki w której znajduje się kursor w górę/dół.
  • Tab/⌘+] - dodaj wcięcie (wcięcie w prawo)
  • Shit+Tab/⌘+[ - usunięcie wcięcia (wycięcie w lewo)

Dodawanie postów:

  • Ctrl+Enter - dodaj post
  • ⌘+Enter - dodaj post (MacOS)