View Full Version : [.NET] Perchè il goto è così usato?
tomminno
11-03-2008, 11:57
A me hanno sempre detto di evitare il goto come la peste e infatti non l'ho mai usato in vita mia.
Però stavo notando che quando si guardano esempi in C/C++ dall'MSDN qualche goto si trova sempre.
goto si trovano in quantità non trascurabili pure nei sorgenti C++ del .NET e negli assembly che lo compongono. :muro:
E' una tecnica da riscoprire?
Non ci credo :eek: Mi posti qualche link ?
tomminno
11-03-2008, 13:05
Non ci credo :eek: Mi posti qualche link ?
Nei sorgenti C/C++ del .NET sscli20 il goto è usato 3289 volte in ben 428 file.
E ci sono almeno 130 file C# che fanno uso del goto.
Difficile pensare che abbiano scritto il .NET 2 volte.
Per quanto riguarda gli assembly l'ho trovato guardando con Reflector nei metodi:
Send e SendAsync di SmtpClient
BeginGetRequestStream, BeginGetResponse, CheckResubmit in HTTPWebRequest
DoBeginAccept, DoDownLevelSendFileCallback di Socket
GetByteCount in UTF8Encoding.
Sembrerebbe una pratica ben consolidata, ho visto il goto usato per uscire da un for( ; ; ) e tante mostruosità simili.
Chi diceva che i framework sono scritti da persone ipercompetenti?
banryu79
11-03-2008, 13:05
E' una tecnica da riscoprire?
Direi proprio di no :D
Probabilmente, dico probabilmente, avranno avuto delle buone ragioni per fare così (quali, non lo so).
Ma avevo letto proprio la settimana scorsa un articolo su MSDN circa i delegates, le callback e i goto, vediamo se lo trovo.
Cmq il goto in genere è preferibile evitarlo avendo a disposizione altre alternative, questo è ovvio.
cdimauro
11-03-2008, 13:11
Sembrerebbe una pratica ben consolidata, ho visto il goto usato per uscire da un for( ; ; ) e tante mostruosità simili.
Chi diceva che i framework sono scritti da persone ipercompetenti?
Io sono "di quelli". :D
Personalmente trovo sia una pratica assolutamente deprecabile, ma prima di giudicare vorrei capire le motivazioni che stanno alla base di queste decisioni.
Sembrerebbe una pratica ben consolidata, ho visto il goto usato per uscire da un for( ; ; ) e tante mostruosità simili.
:eekk: un break gli faceva schifo ? :mad:
io vorrei solo dire di evitare di prendere per oro colato le puttanate che diceva Dijkstra :D
per carità, un grande matematico e il suo famoso algoritmo è di importanza cruciale, ma l'ingegneria del software evidentemente è un'altra cosa :Prrr:
cdimauro
11-03-2008, 14:03
Saranno pure puttanate, ma è da più di vent'anni che non scrivo un GOTO e non ne sento affatto l'esigenza.
Per me l'era degli spaghetti-BASIC è finita da due decadi buone. ;)
per carità, un grande matematico e il suo famoso algoritmo è di importanza cruciale, ma l'ingegneria del software evidentemente è un'altra cosa :Prrr:
Fai vedere un goto a fek e ti ritrovi a mangiare per dieci mesi con la cannuccia :O
Saranno pure puttanate, ma è da più di vent'anni che non scrivo un GOTO e non ne sento affatto l'esigenza. evidentemente è più di vent'anni che programmi solo in piattaforme managed (fammi indovinare, Python? :D). a me quando programmo in C++ (per farti contento non ho detto "C o C++", ho detto direttamente "C++" :D) i goto risparmiano molte linee di codice che altrimenti andrebbe ripetuto più volte; trattandosi perlopiù di codice di cleanup i goto non li uso per niente negli ambienti managed, dove il 99,99% del cleanup viene fatto grazie al garbage collector.
tutto ciò non toglie che sarei estremamente curioso di conoscere le necessità che hanno spinto i programmatori in Microsoft a fare un uso così pesante dei goto in una piattaforma managed.
Davvero usi i goto ? :eekk: Pussa via :D
ah, tra l'altro tanto che siamo in argomento di misteri del .NET mi piacerebbe anche sentire i vostri pareri circa un'altro curiosissimo fatto, ovvero la mancanza delle eccezioni checked. ho aperto un topic tempo fa, ora ve lo ripesco.
edit - http://www.hwupgrade.it/forum/showthread.php?t=1677844
Davvero usi i goto ? :eekk: Pussa via :D ribadisco... mi fanno risparmiare LOC; molte LOC :stordita:
71104: hai mai provato ad usare le eccezioni in C++ ? Dicono che facciano risparmiare LOC, molte LOC :sofico:
cdimauro
11-03-2008, 15:06
evidentemente è più di vent'anni che programmi solo in piattaforme managed (fammi indovinare, Python? :D).
Python lo conosco e ci lavoro da 3 anni. :cool:
Fino a pochi anni prima lavoravo anche in assembly, dove ovviamente i "goto" erano indispensabili, ma per il resto, con linguaggi ad alto livello, da vent'anni a questa parte non ho avuto l'esigenza di "esplicitare" un salto. ;)
a me quando programmo in C++ (per farti contento non ho detto "C o C++", ho detto direttamente "C++" :D) i goto risparmiano molte linee di codice che altrimenti andrebbe ripetuto più volte;
Ho evidenziato il tuo problema fondamentale: quello di RAGGRUPPARE il codice, come ingegneria del software comanda da EONI. :read: :Prrr:
71104: hai mai provato ad usare le eccezioni in C++ ? Dicono che facciano risparmiare LOC, molte LOC :sofico: si, e interferiscono con lo Structured Exception Handling :asd:
be' a parte il SEH, quando posso le uso ma non c'entra niente con la storia dei goto. la mia tipica situazione da programmazione Win32 è la seguente: devo chiamare in ordine una dozzina di funzioni, ciascuna delle quali potrebbe fallire e nel caso richiederebbe il cleanup di tutto ciò che hanno fatto le precedenti. che faccio, un diverso exception handler per ciascun possibile codice di cleanup? non è questo il mio concetto di risparmiare LOC :Prrr:
oppure scrivo un diverso codice di cleanup per ciascun possibile fallimento? no, non ci siamo neanche adesso.
due valide soluzioni al problema sono:
1) invertire tutti gli if che controllano i fallimenti in modo tale da innestarli tutti quanti e rendere uniche le linee di cleanup; ma 12 livelli di indentazione francamente non mi garbano :sofico:
2) una dozzina di labels in cui distribuire le varie linee di codice di cleanup; non posso farci niente, è l'unica :O
tomminno
11-03-2008, 15:10
trattandosi perlopiù di codice di cleanup i goto non li uso per niente negli ambienti managed, dove il 99,99% del cleanup viene fatto grazie al garbage collector.
E fai male, visto che anche in ambienti managed le risorse vanno rilasciate.
Prova a richiamare un webservice o a fare una connessione ad un db senza usare il dispose, vedrai come metti in crisi le macchine.
In C# esiste il comodissimo using, ma è comunque un cleanup fatto dal programmatore non dal GC.
tutto ciò non toglie che sarei estremamente curioso di conoscere le necessità che hanno spinto i programmatori in Microsoft a fare un uso così pesante dei goto in una piattaforma managed.
I goto sono usati esattamente come sono usati in C: nel caso di UTF8Encoding servono a "muoversi" tra una parte e l'altra del ciclo che analizza i singoli caratteri.
In ogni caso si vede che, dove viene usato il goto, c'è molta poca OOP e metodi lunghi centinaia di righe.
Ah ok...ho capito il problema...sentiamo fek cosa suggerirebbe di fare per una soluzione del genere...
cdimauro
11-03-2008, 15:18
Spezzare le ditine al programmatore che ha scritto quel codice, ovviamente... :O
:asd:
In C# esiste il comodissimo using giusto, però comunque ti risparmia dal goto.
I goto sono usati esattamente come sono usati in C non mi interessava il come, ma il perché. e mi interessava una spiegazione fornita da qualcuno di Microsoft :stordita:
In ogni caso si vede che, dove viene usato il goto, c'è molta poca OOP e metodi lunghi centinaia di righe. tralasciando per ora il possibile cattivo design e concentrandomi solo sui goto: io trovo difficile credere che nel progettare le features del C# la Microsoft abbia fatto scelte affrettate e non ponderate. quella delle eccezioni esclusivamente unchecked infatti sembra una scelta molto studiata (a proposito, qualcuno risponde a quel topic? :cry: ), e allo stesso modo vorrei capire cosa ha spinto Microsoft ad introdurre i goto nel C#.
Ah ok...ho capito il problema...sentiamo fek cosa suggerirebbe di fare per una soluzione del genere... ti riferisci al mio post o a quello di tomminno?
ti riferisci al mio post o a quello di tomminno?
Al tuo sorry...conoscendo un po' le API Win32 capisco benissimo la situazione a cui ti riferisci ;)
conoscendo un po' le API Win32 capisco benissimo la situazione a cui ti riferisci ;) ah ma guarda che non è solo questione di Win32 eh: gli stessi scenari mi si presentano puntualmente tali e quali anche con malloc/free, realloc/free, fopen/fclose, costruttore di ifstream e metodo fail, costruttore di ofstream e metodo fail anche lì... addirittura con new e delete :asd:
edit - e poi la sai la cosa divertente? certe volte ho anche provato a ridurre il codice di cleanup affidandomi al fatto che quando il processo termina la sua memoria virtuale scompare e tutti i suoi HANDLE vengono chiusi (e di conseguenza non ha realmente senso liberarsi di molte risorse che in realtà vanno tenute fino alla fine dell'esecuzione). i problemi di questo approccio sono:
1) se il codice cambia e alcune risorse non devi più tenerle fino alla fine ma puoi liberarle prima, devi rintracciare tutte le loro allocazioni e scrivere le corrispondenti deallocazioni; per esperienza personale posso dirti che troppi dettagli potresti tralasciare quando effettui sul codice operazioni del genere in un secondo momento anziché in fase di prima scrittura... almeno per me è così.
2) in Win32 certe risorse (quelle di User32 e GDI32) non se ne vanno da sole quando il processo termina; tempo fa ho letto su MSDN che è questa la causa di certi errori di visualizzazione delle icone del desktop che capitano ogni tanto (a dire il vero in Windows 2000 avevo l'impressione di vederli più spesso che in XP, chissà perché; forse è solo questione di hash tables più grosse).
3) il punto 2 si può estendere ai files temporanei: quelli se non li cancelli non se ne vanno in qualunque piattaforma.
Un conto sono 12 istruzioni API ognuna con una sequenza di istruzioni di pulizia diversa, un altro sono poche istruzioni con diversa gestione degli errori, lì ci stanno bene le eccezioni. Se in quel caso non riesci a farlo in maniera semplice senza il goto significa che devi riprogettare la struttura ad oggetti...
cdimauro
11-03-2008, 16:02
ah ma guarda che non è solo questione di Win32 eh: gli stessi scenari mi si presentano puntualmente tali e quali anche con malloc/free, realloc/free, fopen/fclose, costruttore di ifstream e metodo fail, costruttore di ofstream e metodo fail anche lì... addirittura con new e delete :asd:
Tutto qui? E' ora di passare a Python allora:
with open('Pippo.txt', 'wb') as f:
f.write('Fai i tuoi porci comodi, a chiudere il file ci penso io.')
with MyMutex:
print "Sto accedendo all'area critica. Tranquillo: al release ci penso io!"
Tutto qui? E' ora di passare a Python allora: come ho già detto non uso mai i goto negli ambienti managed. inoltre ci sono cose che non so se riuscirei a fare in Python, e anche se fosse possibile a occhio direi che mi farei solo del male. ad esempio in questo periodo mi sto dilettando a creare un desktop manager (ne ho visti a decine in giro ma nemmeno uno decente) che mostri N pulsanti in una desk band, ciascuno corrispondente ad un desktop; per fare ciò devo anzitutto implementare la desk band (cosa che in Windows si fa scrivendo un oggetto COM, e tanti cari saluti a Python :asd: ), e poi devo gestire i desktop virtuali con le apposite API Win32.
cdimauro
11-03-2008, 16:39
Uomo di poca fede: http://sourceforge.net/projects/pywin32/ :O :D
http://aspn.activestate.com/ASPN/docs/ActivePython/2.3/pywin32/PyWin32.html
kernel::panic
11-03-2008, 18:39
Come diceva prima cionci, anche secondo me basterebbe usare le eccezioni... io perlomeno le uso perchè odio il goto :p
Per fare un esempio (PS: è anche più comodo da loggare perchè si mette una unica volta nel catch la chiamata al logger):
FILE *pFile=NULL;
HANDLE hMutex=NULL;
int *piBuffer=NULL;
try
{
pFile=fopen("c:\\pippo.txt","w+");
if(!pFile) throw exception("cippa lippa");
hMutex=CreateMutex(.....);
if(!hMutex) throw exception("pippo & pluto");
// La new lancia già una std::bad_alloc se non c'è std::nothrow
piBuffer=new int[1234];
........
}
catch(const exception &ex)
{
CLog::Put() << "E' successo un bel casino: " << ex.what() << endl;
}
if(pFile) fclose(pFile);
if(hMutex) ReleaseMutex(hMutex);
delete piBuffer;
Se invece sono richieste performance ultra-super-turbo :D allora il goto è molto più performante del try...catch (e anche del try...finally, senza catch, del c#). Lo stesso kernel di linux ne fa uso (http://kerneltrap.org/node/553/2131); probabilmente anche quello di win ma, essendo closed, non ci è dato saperlo :D
Ciao
cdimauro
11-03-2008, 20:01
Onestamente mi sa troppo di codice C-style. Preferisco questo:
if(FILE *pFile=fopen("c:\\pippo.txt","w+")) {
try
if (HANDLE hMutex=CreateMutex(.....) {
try
// La new lancia già una std::bad_alloc se non c'è std::nothrow
if (int *piBuffer = new int[1234]) {
try {
// Do something...
}
catch(const exception &ex)
CLog::Put() << "E' successo un bel casino lavornado col buffer: " << ex.what() << endl;
delete piBuffer;
}
else
throw exception("Allocazione buffer fallita!");
catch(const exception &ex)
CLog::Put() << "E' successo un bel casino lavorando dentro il mutex: " << ex.what() << endl;
ReleaseMutex(hMutex);
}
else
throw exception("Creazione mutex fallita!");
catch(const exception &ex)
CLog::Put() << "E' successo un bel casino lavorando col file: " << ex.what() << endl;
fclose(pFile);
}
else
throw exception("Apertura file fallita!");
Ovviamente sto assumendo, come te, che dentro la sezione catch non venga sollevata un'eccezione, altrimenti anche quella andava "blindata" dentro un try/catch. ;)
Se invece sono richieste performance ultra-super-turbo :D allora il goto è molto più performante del try...catch (e anche del try...finally, senza catch, del c#).
Questo sarebbe da vedere.
Lo stesso kernel di linux ne fa uso (http://kerneltrap.org/node/553/2131); probabilmente anche quello di win ma, essendo closed, non ci è dato saperlo :D
Ciao
Il kernel di Linux fa ampio uso del goto semplicemente perché il suo autore lo ritiene un utile costrutto (e te pareva). :rolleyes:
Direttamente dal link che hai postato:
I think goto's are fine, and they are often more readable than large
amounts of indentation. That's _especially_ true if the code flow isn't
actually naturally indented (in this case it is, so I don't think using
goto is in any way _clearer_ than not, but in general goto's can be quite
good for readability).
Of course, in stupid languages like Pascal, where labels cannot be
descriptive, goto's can be bad. But that's not the fault of the goto,
that's the braindamage of the language designer.
Linus
Il Pascal viene criticato soltanto perché le etichette del goto non possono essere identificatori "tradizionali", non in quanto tali! :muro:
"Dimenticando", tra l'altro, che da una cinquantina d'anni a questa parte l'uso del goto nella letteratura informatica è severamente deprecato, tant'è che lo stesso Wirth (creatore del Pascal) l'ha COMPLETAMENTE RIMOSSO dai successivi linguaggi che ha progettato.
La madre degli pseudo-programmatori è sempre incinta... :muro:
Uomo di poca fede: http://sourceforge.net/projects/pywin32/ :O :D
http://aspn.activestate.com/ASPN/docs/ActivePython/2.3/pywin32/PyWin32.html omg ma guarda te oh :D
ma sta roba di preciso mi permetterebbe di scrivere in Python una DLL da usare come in-process server? anche esportando le funzioni DllCanUnloadNow, DllRegisterServer, DllGetClassObject e DllUnregisterServer? e Python supporta l'ereditarietà di interfacce multiple? perché una desk band è un oggetto che deve implementare almeno tre interfacce diverse.
Per fare un esempio (PS: è anche più comodo da loggare perchè si mette una unica volta nel catch la chiamata al logger):
[...]
if(pFile) fclose(pFile);
if(hMutex) ReleaseMutex(hMutex);
delete piBuffer;
questa soluzione contiene del codice ridondante: le condizioni di fallimento vengono controllate due volte (durante il proseguimento dell'algoritmo e durante il cleanup). io le duplicazioni di codice le odio sia quando programmo in maniera "bella" e pulita in un ambiente OO e managed sia quando faccio porcate con Win32 :)
probabilmente anche quello di win ma, essendo closed, non ci è dato saperlo :D di sicuro Windows non fa uso di try/catch nel kernel dato che è scritto in C.
Questo sarebbe da vedere. vabbè Cesare, non esageriamo adesso... ok le piattaforme managed ma stai paragonando l'istanziazione nell'heap di una classe (l'eccezione) con un jump incondizionato :D
edit - senza contare poi l'algoritmo di ricerca dell'exception handler lungo il call stack; ora permettimi, anche se non ho fatto test approfonditi, che un catch deve pesare necessariamente molto di più di un jump (incondizionato poi, una delle istruzioni più semplici che ci siano).
Il kernel di Linux fa ampio uso del goto semplicemente perché il suo autore lo ritiene un utile costrutto (e te pareva). :rolleyes: si appunto ragazzi, abbiamo datto del puttanaro a Dijkstra quindi evitiamo di idolatrare quell'incivile incompetente di Torvalds :asd:
si appunto ragazzi, abbiamo datto del puttanaro a Dijkstra quindi evitiamo di idolatrare quell'incivile incompetente di Torvalds :asd:
Non l'ho capita questa.
Dijkstra amava i goto oppure sarebbe difficile costruire l'algoritmo di Dijkstra senza goto? La seconda non e' vera...
cdimauro
11-03-2008, 20:55
omg ma guarda te oh :D
Tzé! Python è onnipotente. :O :asd:
ma sta roba di preciso mi permetterebbe di scrivere in Python una DLL da usare come in-process server? anche esportando le funzioni DllCanUnloadNow, DllRegisterServer, DllGetClassObject e DllUnregisterServer?
Non mi sono mai cimentato con queste cose onestamente, ma penso che per creare una DLL "farlocca" in cui integrare l'interprete Python non ci voglia molto.
Python è un linguaggio fortemente propenso sia alla sua estensione che all'integrazione in altre applicazioni (DLL incluse, quindi): http://docs.python.org/ext/ext.html
e Python supporta l'ereditarietà di interfacce multiple? perché una desk band è un oggetto che deve implementare almeno tre interfacce diverse.
Python supporta l'ereditarietà multipla, "alla C++", per cui sulla carta non avrebbe difficoltà.
Sulla desk band in particolare non so niente, ma qui http://aspn.activestate.com/ASPN/docs/ActivePython/2.3/pywin32/Python.2c_C.2b.2b.2c_and_COM.html trovi un esempio di utilizzo di un oggetto COM, mentre qui http://aspn.activestate.com/ASPN/docs/ActivePython/2.3/pywin32/win32com.shell_and_Windows_Shell_Links.html usa la shell.
Mi fermo qui perché, come ho detto, su quanto chiedi non so nulla e non amo sparare puttanate come Torvalds. :asd:
si, e interferiscono con lo Structured Exception Handling :asd:
Giustificare un errore (usare i goto) con un altro (programmare in windows) non e' una buona cosa :asd:
Battute a parte, non mi vengono in mente molti casi in un cui abbia un senso, a parte
che nell'implementazione di funzionalita' di piu' alto livello (ad esempio la gestione delle eccezioni stessa). In particolare non mi e' chiaro il tuo esempio... puoi essere piu' esplicito ?
Uomo di poca fede: http://sourceforge.net/projects/pywin32/ :O :D
http://aspn.activestate.com/ASPN/docs/ActivePython/2.3/pywin32/PyWin32.html
ipse dixit :o.
Ho avuto modo di implementare oggetti com e anche servizi in python, ed e' una vera sciocchezza (e lo dice uno che la programmazione in Windows la conosce poco).
edit - senza contare poi l'algoritmo di ricerca dell'exception handler lungo il call stack; ora permettimi, anche se non ho fatto test approfonditi, che un catch deve pesare necessariamente molto di più di un jump (incondizionato poi, una delle istruzioni più semplici che ci siano).
Beh, un jump non locale e' una bestia decisamente diversa. Se invece ti riferisci sempre al solo jump locale probabilmente il costo dello stack unwind dovuto alla gestione delle eccezioni puo' essere ottimizzata senza problemi, mentre con la jump devi stare piu' attento (vedi mio post successivo)
cdimauro
11-03-2008, 21:11
vabbè Cesare, non esageriamo adesso... ok le piattaforme managed ma stai paragonando l'istanziazione nell'heap di una classe (l'eccezione) con un jump incondizionato :D
edit - senza contare poi l'algoritmo di ricerca dell'exception handler lungo il call stack; ora permettimi, anche se non ho fatto test approfonditi, che un catch deve pesare necessariamente molto di più di un jump (incondizionato poi, una delle istruzioni più semplici che ci siano).
Qui c'è un problema di fondo da chiarire.
Se dobbiamo usare le eccezioni, non possiamo farlo com'è stato (anche nell'esempio che ho portato io) utilizzando gli if per controllare la restituzione o meno di una risorsa: stiamo programmando ancora in maniera "tradizionale" (sebbene le try/catch aiutino a sistemare meglio il codice).
Con le eccezioni io NON dovrei mettere NESSUN if, visto che al primo utilizzo della risorsa dovrebbe esser generata l'apposita eccezione.
Il codice, quindi, sarebbe perfettamente lineare e privo del benché minimo controllo che comporta SEMPRE un relativo salto CONDIZIONALE (i peggiori della specie, lo sai) nella soluzione "classica".
In soldoni, mi aspetterei roba così (lo scrivo in Python per sbrigarmi prima :D):
try:
f = open('pippo')
try:
print 'La prima riga è:', f.readline()
except IOError:
print 'Errore di lettura ci fu!'
finally:
f.close()
except:
print 'Errore di apertura file ci fu!'
ZERO if, insomma, al contrario del codice tradizionale che ha SEMPRE un if e relativo salto.
Il che, permettimi, è MOLTO differente in termini prestazionali, visto che la creazione dell'oggetto eccezione avviene esclusivamente nel momento in cui effettivamente bisogna generarla. ;)
x marco.r: grazie della tua testimonianza. :)
Comunque... eretico!!! Windows è er mejo che ci possa essere. :O
questa soluzione contiene del codice ridondante: le condizioni di fallimento vengono controllate due volte (durante il proseguimento dell'algoritmo e durante il cleanup). io le duplicazioni di codice le odio sia quando programmo in maniera "bella" e pulita in un ambiente OO e managed sia quando faccio porcate con Win32 :)
E' ridondante perche' e' scritto piu' alla C che alla C++.
In un mondo ideale sia i file che i mutex sono oggetti che liberano automaticamente le risorse quando distrutti e che quindi lavorano bene col meccanismo delle eccezioni. Un esempio abbastanza vicino si potrebbe fare con gli fstream della libreria standard e i mutex delle boost:
try
{
std::ofstream out("c:\\pippo.txt","w+");
boost::thread::scoped_lock( ... );
piBuffer=new int[1234];
// ...
}
catch(const exception &ex)
{
CLog::Put() << "E' successo un bel casino: " << ex.what() << endl;
}
// look ma, no code cleanup !
Per inciso in questo caso ho usato scoped_lock per cui se durante il blocco try{...} qualcun altro lancia una eccezione mentre teniamo il mutex, la risorsa viene liberata. L'alternativa e' controllare _tutte_ le chiamate a funzioni metodi (anche quelli dichiarati throw()!) con dey try...catch nested.
In altri casi potrei non volerlo fare, e allora usero' un mutex "standard"
kernel::panic
12-03-2008, 07:20
E' ridondante perche' e' scritto piu' alla C che alla C++.
In un mondo ideale sia i file che i mutex sono oggetti che liberano automaticamente le risorse quando distrutti e che quindi lavorano bene col meccanismo delle eccezioni.
Esattamente! Il problema è proprio questo: le API dei sistemi operativi sono scritte in C (per cui no eccezioni), e sono poche le librerie scritte in C++ che ne fanno uso. Le boost ad esempio le usano e permettono la scrittura di codice "pulito" come nel tuo esempio.
In ambiente MS mi è capitato di usare ALT/MFC, che non usano le eccezioni, però incapsulano gli handle di sistema nelle classi (CRegKey, CMutex, ecc). Quindi non c'è bisogno di fare il cleanup: viene già fatto dal distruttore quando termina lo scoop.
...scusate l'ignoranza...programmo in java dove il goto è riservato ma non utilizzabile...come mai questo goto è tanto bistrattato?...se esiste come funzione perchè è ritenuto una porcata?...
...ciao...
cdimauro
12-03-2008, 10:54
http://en.wikipedia.org/wiki/Spaghetti_code
Con le eccezioni io NON dovrei mettere NESSUN if, visto che al primo utilizzo della risorsa dovrebbe esser generata l'apposita eccezione. non se ti ritrovi una funzione già pronta che non lancia nessuna eccezione ma restituisce codici di errore; oppure che fa entrambe le cose (ne esistono tra le Win32).
e ad ogni modo ammettendo anche l'if oltre al jump del goto l'allocazione di un blocco di heap e chiamata al costruttore dell'eccezione su Windows costa comunque di più (tra chiamate a funzioni varie del runtime di Visual C++, chiamate della Heap API di Win32, eventuali chiamate al Virtual Memory Manager con conseguente switch in kernel mode se necessario, ritorno all'user mode, chiamata al costruttore, e chi più ne ha più ne metta).
Il che, permettimi, è MOLTO differente in termini prestazionali, visto che la creazione dell'oggetto eccezione avviene esclusivamente nel momento in cui effettivamente bisogna generarla. ;) questo è vero, ma tanto l'if su Windows ci sta comunque perché l'API quella è, e qualunque framework deve andare a finire per forza là. l'eccezione la lancia o non la lancia solo perché controlla che tutto sia andato bene con un if.
Esattamente! Il problema è proprio questo: le API dei sistemi operativi sono scritte in C veramente le Win32 sono scritte in C++; sono le funzioni esposte ad essere puramente C (e neanche tutte: vedi le miriadi di interfacce COM, o addirittura la GDI+).
(per cui no eccezioni) capisco che tu sia abituato a quella schifezza di Linux dove al massimo puoi trovare i segnali ( :Puke: ), ma Windows le eccezioni le ha eccome: usa un meccanismo che si chiama SEH (Structured Exception Handling).
e sono poche le librerie scritte in C++ che ne fanno uso. tutte le librerie, indipendentemente dal linguaggio in cui sono scritte, devono direttamente o indirettamente andare a finire nelle API o nelle syscall che dir si voglia.
In ambiente MS mi è capitato di usare ALT/MFC, [...] *ATL
[...] Quindi non c'è bisogno di fare il cleanup: viene già fatto dal distruttore quando termina lo scoop. *scope
...scusate l'ignoranza...programmo in java dove il goto è riservato ma non utilizzabile...come mai questo goto è tanto bistrattato?...se esiste come funzione perchè è ritenuto una porcata?... chiedilo a Dijkstra: l'ha detto lui, mica noi :D
kernel::panic
12-03-2008, 14:14
capisco che tu sia abituato a quella schifezza di Linux
de gustibus :rolleyes:
Windows le eccezioni le ha eccome: usa un meccanismo che si chiama SEH (Structured Exception Handling).
Questo non lo sapevo, l'ho imparato ora... però lasciami dire che costrutti così non sono molto C/C++ standard:
VOID main(VOID)
{
__try
{
__try
{
RaiseException(1, // exception code
0, // continuable exception
0, NULL); // no arguments
}
__finally
{
printf("2 "); // this is printed second
}
}
__except ( FilterFunction() )
{
printf("3\n"); // this is printed last
}
}
*ATL
*scope
Quando ho scritto ero un po' di fretta, dovevo piazzarmi davanti alla TV per vedere l'Inter perd... ehm giocare! :D :D
Ciao
de gustibus :rolleyes: no, non si tratta di gusti... i segnali fanno proprio oggettivamente schifo :asd:
Questo non lo sapevo, l'ho imparato ora... però lasciami dire che costrutti così non sono molto C/C++ standard:
1) e a me?
2) certo se poi tu dichiari il main come void, anzi VOID... :rolleyes:
3) sbaglio o ci mancava una printf("1 ") ? :mbe:
tomminno
12-03-2008, 14:44
Questo non lo sapevo, l'ho imparato ora... però lasciami dire che costrutti così non sono molto C/C++ standard:
Non sono standard, ma ti mettono al riparo da dereferenziazione di puntatori nulli/non istanziati, stack overflow e chi più ne ha più ne metta.
Mi sembrava di aver capito però che Microsoft non ne consigliasse l'uso in C++.
Mi sembrava di aver capito però che Microsoft non ne consigliasse l'uso in C++. sarà l'ennesima volta che scrivo che su certi compilatori le eccezioni SEH interferiscono con le eccezioni C++ e viceversa.
kernel::panic
12-03-2008, 15:46
1) e a me?
un grazie era sottinteso ;)
cdimauro
13-03-2008, 07:16
non se ti ritrovi una funzione già pronta che non lancia nessuna eccezione ma restituisce codici di errore; oppure che fa entrambe le cose (ne esistono tra le Win32).
e ad ogni modo ammettendo anche l'if oltre al jump del goto l'allocazione di un blocco di heap e chiamata al costruttore dell'eccezione su Windows costa comunque di più (tra chiamate a funzioni varie del runtime di Visual C++, chiamate della Heap API di Win32, eventuali chiamate al Virtual Memory Manager con conseguente switch in kernel mode se necessario, ritorno all'user mode, chiamata al costruttore, e chi più ne ha più ne metta).
questo è vero, ma tanto l'if su Windows ci sta comunque perché l'API quella è, e qualunque framework deve andare a finire per forza là. l'eccezione la lancia o non la lancia solo perché controlla che tutto sia andato bene con un if.
Alberto, il problema è che continui a ragionare in termini di C e non di C++.
Che ci debba essere ALMENO un if / condizione è cosa naturale: deve accadere, nel normale flusso dell'elaborazione, che da qualche parte qualcuno deve accorgersi che una richiesta non possa andare a buon fine.
Il problema è: come gestire questa condizione d'errore?
La prassi con C & affini è quella della catena di if, dal primo che l'ha rilevata fino all'ultimo che la deve poi gestire. Tutti if condizionali, che, come sai, sono i peggiori da trattare per un processore.
In C++ la prassi sarebbe: al primo if sollevo una precisa eccezione, che viene intercettata dal primo handler "utile". Quindi un solo if condizionale e basta.
Il guadagno mi sembra evidente: a parte il primo if che è comune a entrambi, nel primo caso c'è la penalizzazione di effettuare SEMPRE controlli sul risultato, mentre nel secondo non c'è nessun if e tra l'altro l'eccezione viene costruita soltanto quando si verifica.
Questo a livello teorico, raffrontando un approccio tradizionale a uno basato sulle eccezioni.
Poi se nella pratica abbiamo sistemi che sono basati esclusivamente sul primo, oppure che sono un misto fra il primo e il secondo, ne prendo atto, non c'è problema. ;)
è bello notare (almeno ai miei tempi) come questo costrutto :
http://en.wikipedia.org/wiki/Spaghetti_code
10 i = 0
20 i = i + 1
30 PRINT i; " squared = "; i * i
40 IF i < 10 THEN GOTO 20
50 PRINT "Program Completed."
60 END
fosse bellamente inculcato nelle nostre giovani menti...almeno fino alla fine delle superiori :confused:
anche in pascal... :(
ora mi chiedo, se una cosa è "sbagliata" o è meglio non usarla per tanti motivi...non sarebbe meglio non insegnarla nemmeno, specialmente nelle classi inferiori, e trattarlo solamente come "distinguo" nei corsi superiori??
oddio magari ora è cosi... spero :)
ps per quanto riguarda torvalds, io non ne capisco una mazza di queste cose a questo livello, quindi non uccidetemi... il costrutto goto avrà qualche pregio? tipo la velocità di esecuzione? forse linus è convinto di gestire tutti i problemi del goto a livello di ingegnerizzazione del kernel, e "beneficiare" di qualche pregio di goto?? altrimenti perchè lo fa?? :)
Mai fatto il goto alle superiori...sia in C che in Pascal ;)
Mai fatto il goto alle superiori...sia in C che in Pascal ;)
beato... vallo a dire alla mia professoressa che non sapeva neanche accenderlo il pc eh eh... una volta mi pare in 4, ci ritrovammo a disegnare un coniglio in codice ascii in pascal :doh: mooolto utile....
cosa? il c? mai visto :) solo basic (ma il gwBasic!!) e pascal....
ah che mondo...:help:
WhiteWolf42
13-03-2008, 08:32
Mai fatto il goto alle superiori...sia in C che in Pascal ;)
l'ho usato una volta .... voto -> 2, da quel momento ho capito ... goto-> BRUTTO
cosa? il c? mai visto :) solo basic (ma il gwBasic!!) e pascal....
A dire la verità era C++, ma praticamente non abbiamo mai fatto le classi :muro:
da noi se qualcuno si azzardava a usare il goto il prof gli staccava un braccio a morsi :asd:
stessa cosa per le variabili globali :asd:
comunque per dire la mia.. il goto forse (e dico forse) è utilizzabile quando si ha a che fare con codice di basso livello (OS, driver ecc..) dove il più delle volte abbiamo rinunciato alla leggibilità molto prima di avere introdotto un banalissimo goto.
se parliamo di tutti gli altri casi è un costrutto assolutamente inutile.
il problema è che meno LOC non implica necessariamente che il codice sia più leggibile, anzi io mi aspetterei che oltre una certa soglia diventi meno leggibile.
in ogni caso secondo me il framework .NET è un pochino offuscato da qualche software.. oppure la mente di chi l'ha scritto è offuscata :asd:
o magari semplicemente si tratta di ottimizzazioni create in automatico a partire dal sorgente originale
da noi se qualcuno si azzardava a usare il goto il prof gli staccava un braccio a morsi :asd:
stessa cosa per le variabili globali :asd:
comunque per dire la mia.. il goto forse (e dico forse) è utilizzabile quando si ha a che fare con codice di basso livello (OS, driver ecc..) dove il più delle volte abbiamo rinunciato alla leggibilità molto prima di avere introdotto un banalissimo goto.
se parliamo di tutti gli altri casi è un costrutto assolutamente inutile.
il problema è che meno LOC non implica necessariamente che il codice sia più leggibile, anzi io mi aspetterei che oltre una certa soglia diventi meno leggibile.
in ogni caso secondo me il framework .NET è un pochino offuscato da qualche software.. oppure la mente di chi l'ha scritto è offuscata :asd:
o magari semplicemente si tratta di ottimizzazioni create in automatico a partire dal sorgente originale
Quoto tutto.
Mai vista una label in C#, su nessuno dei miei e degli altrui programmi.
Neanche se ne sente la necessita'.
Quoto praticamente tutto tranne il fatto che sia un costrutto assolutamente inutile. Per me e' addirittura dannoso (non per la velocita' chiaro, ma per la leggibilita').
Si possono fare grandi "danni" anche senza il goto comunque.
esatto :D sono stato troppo buono con il goto :p
WhiteWolf42
13-03-2008, 09:13
quoto & aggiungo: oltre alla leggibilità ne perde molto anche la manutenzione e ls sicurezza. I salti incondizionati sono SEMPRE pericolosi.
L'unica eccezione IMHO la si può concepire quando si scrive un driver ... in quel caso le performance sono il punto n°1 ... in tutti gli altri casi: CROCEFISSO IN SALA MENSA !!!
allora se un programmatore ha i cosiddetti OO
può usare il goto per velocizzare il codice (vedi linus) se riesce a non fare casini e anche se si perde di leggibilità e manutenzione, in alcuni casi, dove la performance viene prima di tutto può essere accettato..?
una specie di tricks da usare con coscenza e metodo... :)
allora se un programmatore ha i cosiddetti OO
può usare il goto per velocizzare il codice (vedi linus) se riesce a non fare casini e anche se si perde di leggibilità e manutenzione, in alcuni casi, dove la performance viene prima di tutto può essere accettato..?
una specie di tricks da usare con coscenza e metodo... :)
hai deciso di scatenare le ire di cdimauro per caso? :asd:
mindwings
13-03-2008, 12:10
allora se un programmatore ha i cosiddetti OO
può usare il goto per velocizzare il codice (vedi linus) se riesce a non fare casini e anche se si perde di leggibilità e manutenzione, in alcuni casi, dove la performance viene prima di tutto può essere accettato..?
una specie di tricks da usare con coscenza e metodo... :)
quei tricks rendono il codice poco comprensibile ad altre persone...
Anche a distanza di tempo dubito che una persona si ricordi il perchè di un salto...(incondizionato)
banryu79
13-03-2008, 12:57
allora se un programmatore ha i cosiddetti OO
può usare il goto per velocizzare il codice...?
Più che il codice velocizza la rotazione dei cosidetti OO ai suoi colleghi... :asd:
cdimauro
13-03-2008, 13:20
hai deciso di scatenare le ire di cdimauro per caso? :asd:
Le mie ire? Come dicevo, sono SECOLI che non uso il goto in un'applicazione scritta con un linguaggio ad alto livello.
Volete usare i goto? E chi se ne frega: cazzi vostri e di chi poi dovrà leggere e manutere il codice.
Insomma, "beati" gli sviluppatori che lavorano a Linux... :asd:
se era riferito a me...
io non uso il goto :) nn programmo proprio nulla, purtroppo, era semplice curiosità
ciao :D
cdimauro
13-03-2008, 13:37
No, il mio era un discorso generale, volto a chi lo usa. Tu non lo usi, e quindi non ci rientri. :)
Lo stesso kernel di linux ne fa uso (http://kerneltrap.org/node/553/2131); probabilmente anche quello di win ma, essendo closed, non ci è dato saperlo :D
Su Linux vengono usati circa 40000 goto in tutto, su un sorgente con più di 6 milioni di LOC non sono cosi tanti.
Scorrendo velocemente la lista sono quasi tutti:
goto err
goto fail
goto out
che portano a eseguire qualche riga di codice alla fine della funzione. Vengono evidentemente usati per gestire il cleanup. Non avendo eccezioni o clausole with non ci sono molte alternative, a meno di preferire 12 livelli di indentazione.
Inoltre la maggior parte del codice è costituito da driver, in un ambito cosi a basso livello non è certo l'uso di qualche goto che riduce la leggibilità.
Finche si trovano in un kernel e nei driver la cosa non mi stupisce più di tanto, ma in .Net un po si, soprattutto se Mono a quanto pare riesce a farne a meno.
Fai vedere un goto a fek e ti ritrovi a mangiare per dieci mesi con la cannuccia :O
Non c'e' pericolo, fra una scusa e l'altra non scrive una riga di codice in Diamonds da mesi; le sue ditine sono al sicuro ;)
L'utima volta che ho usato un goto, vediamo, ah si', avevo otto anni. A nove ho smesso :)
evidentemente è più di vent'anni che programmi solo in piattaforme managed (fammi indovinare, Python? :D). a me quando programmo in C++ (per farti contento non ho detto "C o C++", ho detto direttamente "C++" :D) i goto risparmiano molte linee di codice che altrimenti andrebbe ripetuto più volte; trattandosi perlopiù di codice di cleanup i goto non li uso per niente negli ambienti managed, dove il 99,99% del cleanup viene fatto grazie al garbage collector.
Se impari a usare i distruttori e/o le eccezioni risparmi ancora piu' righe di codice. Mai scritto un goto in vita mia in C++.
due valide soluzioni al problema sono:
1) invertire tutti gli if che controllano i fallimenti in modo tale da innestarli tutti quanti e rendere uniche le linee di cleanup; ma 12 livelli di indentazione francamente non mi garbano :sofico:
2) una dozzina di labels in cui distribuire le varie linee di codice di cleanup; non posso farci niente, è l'unica :O
3) Usare ObjectGuard e mettere il codice di cleanup nel distruttore. Go learn C++.
questa soluzione contiene del codice ridondante: le condizioni di fallimento vengono controllate due volte (durante il proseguimento dell'algoritmo e durante il cleanup). io le duplicazioni di codice le odio sia quando programmo in maniera "bella" e pulita in un ambiente OO e managed sia quando faccio porcate con Win32 :)
Ooops:
try
{
ScopedFileWrapper file(fopen("c:\\pippo.txt","w+"));
ScopedMutexWrapper mutex(CreateMutex(.....));
auto_ptr<int> buffer(new int[1234]);
........
} // tutti i distruttori sono inovcati qui in ordine inverso automaticamente anche in presenza di eccezioni
catch(const exception &ex)
{
CLog::Put() << "E' successo un bel casino: " << ex.what() << endl;
}
E passa la paura del goto...
PS. In C++ NON si usa la notazione ungherese :)
PS2. Linus, go learn C++, n00b.
edit: non avevo letto il post di marco.r :(
3) Usare ObjectGuard e mettere il codice di cleanup nel distruttore. Go learn C++.
Che è ?
Che è ?
Altro nome per gli ScopedObject. Sono oggetti che prendono una risorsa e la liberano quando si esce dallo scope.
kernel::panic
13-03-2008, 18:15
Oggi cercando alcune cose su internet di C# mi sono imbattuto nel blog di un tizio che diceva di usare (e incitava a farlo!) il goto per uscire dai cicli annidati!! :muro:
PS: Visto che nel C# per usare i puntatori bisogna dichiarare il blocco di codice unsafe {...}, dovrebbero obbligare a fare lo stesso per usare il goto. :D :D
kernel::panic
13-03-2008, 18:25
Su Linux vengono usati circa 40000 goto in tutto, su un sorgente con più di 6 milioni di LOC non sono cosi tanti.
Bhe, facendo la divisione si ottiene una media di 1 goto su 150 LOC... parecchio direi :p ... contando che molte LOC sono graffe o istruzioni messe su più righe (forse ci sono più goto che while{} o do{} while).
Cmq visto che il kernel linux gira bene, basta chiudere un'occhio :Prrr:
Le mie ire? Come dicevo, sono SECOLI che non uso il goto in un'applicazione scritta con un linguaggio ad alto livello.
Volete usare i goto? E chi se ne frega: cazzi vostri e di chi poi dovrà leggere e manutere il codice.
Insomma, "beati" gli sviluppatori che lavorano a Linux... :asd:
nono.. io sono contro i GOTO :D più che altro direi beati gli sviluppatori che lavorano al framework .NET :asd:
^TiGeRShArK^
13-03-2008, 19:03
in ogni caso secondo me il framework .NET è un pochino offuscato da qualche software.. oppure la mente di chi l'ha scritto è offuscata :asd:
o magari semplicemente si tratta di ottimizzazioni create in automatico a partire dal sorgente originale
imho è sicuramente così.
Anche in java, utilizzando diversi decompilatori, in certi casi si ottiene nel codice una label e delle GOTO che ovviamente in java non hanno senso.
Quindi è un artefatto derivante dalla non perfetta decompilazione del bytecode piuttosto che un'incapacità dei programmatori che hanno scritto .Net :p
Su Linux vengono usati circa 40000 goto in tutto, su un sorgente con più di 6 milioni di LOC non sono cosi tanti.
Scorrendo velocemente la lista sono quasi tutti:
goto err
goto fail
goto out
che portano a eseguire qualche riga di codice alla fine della funzione. Vengono evidentemente usati per gestire il cleanup. Non avendo eccezioni o clausole with non ci sono molte alternative, a meno di preferire 12 livelli di indentazione.
Inoltre la maggior parte del codice è costituito da driver, in un ambito cosi a basso livello non è certo l'uso di qualche goto che riduce la leggibilità.
Finche si trovano in un kernel e nei driver la cosa non mi stupisce più di tanto, ma in .Net un po si, soprattutto se Mono a quanto pare riesce a farne a meno.
quoto tutto...
per quanto riguarda microsoft beh, se lo usano come ho letto anche per uscire dai cicli for direi che è allucinante :eek:
^TiGeRShArK^
13-03-2008, 21:01
quoto tutto...
per quanto riguarda microsoft beh, se lo usano come ho letto anche per uscire dai cicli for direi che è allucinante :eek:
:read:
Anche in java, utilizzando diversi decompilatori, in certi casi si ottiene nel codice una label e delle GOTO che ovviamente in java non hanno senso.
Quindi è un artefatto derivante dalla non perfetta decompilazione del bytecode piuttosto che un'incapacità dei programmatori che hanno scritto .Net
:p
Se impari a usare i distruttori e/o le eccezioni risparmi ancora piu' righe di codice. delle eccezioni si è già discusso: se la CreateFile o la SuspendThread o quello che ti pare mi ritornano codici di errore questi per forza di cose vanno esaminati con un if, anche se poi questo if lo uso per lanciare l'eccezione in caso di errore.
per quanto riguarda l'uso dei distruttori: non so come giustificarlo alle mie teorie di ingegneria del software (tipo caso di dissonanza cognitiva :D), ma creare una classe apposta per ogni tipo di risorsa che alloco mi sembra costituire una perdita di tempo molto maggiore rispetto al design basato sui goto o anche semplicemente sul codice di cleanup ridondante. per quanto riguarda la leggibilità dite quello che vi pare ma i miei programmi sono piccoli, e nel mio piccolo tutti sti problemi di leggibilità non li vedo... :ciapet:
anche perché ormai il mio codice Win32 è divenuto molto stereotipato e quindi lo capisco perfettamente.
insomma non credo che ne valga la pena, anche se non ho provato e anche se in teoria ne vale sempre la pena; tipico caso di dissonanza cognitiva :O
Ooops:
try
{
ScopedFileWrapper file(fopen("c:\\pippo.txt","w+"));
ScopedMutexWrapper mutex(CreateMutex(.....));
auto_ptr<int> buffer(new int[1234]);
........
} // tutti i distruttori sono inovcati qui in ordine inverso automaticamente anche in presenza di eccezioni
catch(const exception &ex)
{
CLog::Put() << "E' successo un bel casino: " << ex.what() << endl;
}
E passa la paura del goto... la fai facile, ma le classi ScopedFileWrapper e ScopedMutexWrapper chi le scrive? :D
se stai per dire che me le scrive MFC/ATL, o wxWidgets, o qualche altro framework, mi va benissimo: infatti in quei casi i goto non li uso :O
PS. In C++ NON si usa la notazione ungherese :) a volte la uso per allinearmi alle nomenclature usate da Microsoft, ma mi sfugge dov'è che l'ho usata in questo topic :wtf:
DioBrando
14-03-2008, 01:51
io vorrei solo dire di evitare di prendere per oro colato le puttanate che diceva Dijkstra :D
per carità, un grande matematico e il suo famoso algoritmo è di importanza cruciale, ma l'ingegneria del software evidentemente è un'altra cosa :Prrr:
Dijkstra ha "solo" enucleato in un contesto di IngSW ancora embrionale quello che Bohm e Jacopini avevano dimostrato matematicamente 2 anni prima e cioè che qualsiasi algoritmo può essere modellato ed implementato semplicemente con le 3 strutture fondamentali di ciclo selezione e sequenza, rendendo di fatto inutile l'utilizzo del GoTo.
;)
DioBrando
14-03-2008, 01:56
l'ho usato una volta .... voto -> 2, da quel momento ho capito ... goto-> BRUTTO
"Scusa Egon ho sempre fatto confusione tra bene e male...che intendi?"
"Immagina che la vita per come la conosci si fermasse instantaneamente e le particelle esplodessero alla velocità della luce..."
:D
DioBrando
14-03-2008, 02:02
allora se un programmatore ha i cosiddetti OO
può usare il goto per velocizzare il codice (vedi linus) se riesce a non fare casini e anche se si perde di leggibilità e manutenzione, in alcuni casi, dove la performance viene prima di tutto può essere accettato..?
una specie di tricks da usare con coscenza e metodo... :)
tralasciando Linus&co, quella delle performance è una baggianata colossale ormai :) Sono stati scritti fiumi di inchiostro ma con i compilatori JIT che ci ritroviamo ora, il calo di prestazioni è pressochè irrilevante ed è questo il motivo per cui in questi ultimi anni lo sviluppo si è spostato ad un livello di astrazione + alto con i linguaggi interpretati che hanno preso piede in praticamente tutte le branche di sviluppo del software.
Poi d'accordo, ti serve un'applicazione che giri in ambiente realtime, magari mission critical (siamo già in un contesto di ampia minoranza) e causa forza maggiore parte del codice sarà Assembly (riduciamo ancora di + la fetta di cui sopra), qui userai probabilmente dei GoTo...sì ma nicchia...
kernel::panic
14-03-2008, 07:30
quella delle performance è una baggianata colossale ormai :) Sono stati scritti fiumi di inchiostro ma con i compilatori JIT che ci ritroviamo ora, il calo di prestazioni è pressochè irrilevante ed è questo il motivo per cui in questi ultimi anni lo sviluppo si è spostato ad un livello di astrazione + alto con i linguaggi interpretati che hanno preso piede in praticamente tutte le branche di sviluppo del software.
Se mi parli delle performance tra linguaggi compilati in codice macchina e compilati in IL ti do pienamente ragione :)
Mi sono ricreduto anche io lavorando sia in c++ che in c#: a parte il tempo di startup maggiore dovuto al compilatore JIT l'esecuzione di codice managed è davvero molto veloce, in alcuni casi meglio del codice unmanaged. E soprattutto quando metti l'applicazione su un IA64 non devi ricompilare ;)
Rigurado invece la velocità (all'interno dello stesso linguaggio) tra goto ed exception non sono d'accordo:
static void Main()
{
int t = Environment.TickCount;
for(int i = 0; i < 1000000; ++i) Exce();
Console.WriteLine("EXCE: {0} ms", Environment.TickCount - t);
t = Environment.TickCount;
for(int i = 0; i < 1000000; ++i) GoTo();
Console.WriteLine("GOTO: {0} ms", Environment.TickCount - t);
Console.ReadKey();
}
static void Exce()
{
try
{
for(int i = 0; i < 10; ++i)
{
if(i == 5)
throw new Exception();
}
}
catch
{ }
}
static void GoTo()
{
for(int i = 0; i < 10; ++i)
{
if(i == 5)
goto Exit;
}
Exit: ;
}
Chiaramente è un caso limite, però sul mio PC i risultati sono:
EXCE: 32422 ms
GOTO: 16 ms
Byez :)
tomminno
14-03-2008, 07:44
imho è sicuramente così.
Anche in java, utilizzando diversi decompilatori, in certi casi si ottiene nel codice una label e delle GOTO che ovviamente in java non hanno senso.
Quindi è un artefatto derivante dalla non perfetta decompilazione del bytecode piuttosto che un'incapacità dei programmatori che hanno scritto .Net :p
Magari sarà così per Java.
Peccato che se scarichi i sorgenti del .NET sono identici a quelli visti con Reflector.
Quindi nessun errore di decompilazione.
Hanno usato il goto anche in codice C#.
kernel::panic
14-03-2008, 07:57
Siccome stanno facendo manutenzione al server col DB, e quindi per ora non ho una mazza da fare :D , per par condicio ho fatto lo stesso esempio in c++ (anche qui il goto è più veloce):
#include <windows.h>
#include <iostream>
void Exce()
{
try
{
for(int i = 0; i < 10; ++i)
{
if(i == 5)
throw std::exception();
}
}
catch(...)
{ }
}
static void GoTo()
{
for(int i = 0; i < 10; ++i)
{
if(i == 5)
goto Exit;
}
Exit: ;
}
int main()
{
DWORD t = GetTickCount();
for(int i = 0; i < 1000000; ++i) Exce();
std::cout << "EXCE: " << (GetTickCount() - t) << " ms" << std::endl;
t = GetTickCount();
for(int i = 0; i < 1000000; ++i) GoTo();
std::cout << "GOTO: " << (GetTickCount() - t) << " ms" << std::endl;
char c;
std::cin >> c;
return 0;
}
Risultati:
EXCE: 5016 ms
GOTO: 0 ms
Risultati:
EXCE: 5016 ms
GOTO: 0 ms
Questo perché il compilatore si è accorto che nel for non viene fatto niente ;)
Evidentemente con il goto questa ottimizzazione esiste, mentre con le eccezioni no.
^TiGeRShArK^
14-03-2008, 09:30
Magari sarà così per Java.
Peccato che se scarichi i sorgenti del .NET sono identici a quelli visti con Reflector.
Quindi nessun errore di decompilazione.
Hanno usato il goto anche in codice C#.
da dove si scaricano i sorgenti del .net? :fagiano:
kernel::panic
14-03-2008, 09:43
Questo perché il compilatore si è accorto che nel for non viene fatto niente ;)
Evidentemente con il goto questa ottimizzazione esiste, mentre con le eccezioni no.
Cavolo, c'hai troppo ragione! :p Non pensavo che il compilatore se ne accorgesse :eek:
Modificando i for così:
if(i == 5)
{
GetTickCount();
throw std::exception();
}
if(i == 5)
{
GetTickCount();
goto Exit;
}
ottengo:
EXCE: 5017 ms
GOTO: 16 ms --> Come nel C#
Quindi si deduce che:
- Il compilatore VC++ e più intelligente del VC# :D
- Le eccezioni del C++ sono molto più veloci che nel C# (sempre che anche qui non ci siano ottimizzazioni solo in C++)
- I goto si equivalgono in C++ e C#
la fai facile, ma le classi ScopedFileWrapper e ScopedMutexWrapper chi le scrive? :D
se stai per dire che me le scrive MFC/ATL, o wxWidgets, o qualche altro framework, mi va benissimo: infatti in quei casi i goto non li uso :O
Te le scrivi tu se ne hai voglia, sono tre righe di codice, due se sai usare i template. Altrimenti usi boost.
a volte la uso per allinearmi alle nomenclature usate da Microsoft, ma mi sfugge dov'è che l'ho usata in questo topic :wtf:
La vecchia nomenclatura MS era sbagliata.
per quanto riguarda l'uso dei distruttori: non so come giustificarlo alle mie teorie di ingegneria del software (tipo caso di dissonanza cognitiva :D), ma creare una classe apposta per ogni tipo di risorsa che alloco mi sembra costituire una perdita di tempo
Prendere in mano un libro e imparare ad usare i template ti sembra una perdita di tempo?
tomminno
14-03-2008, 09:47
da dove si scaricano i sorgenti del .net? :fagiano:
Qui (http://www.microsoft.com/downloads/details.aspx?FamilyId=8C09FD61-3F26-4555-AE17-3121B4F51D4D&displaylang=en)
Siccome stanno facendo manutenzione al server col DB, e quindi per ora non ho una mazza da fare :D , per par condicio ho fatto lo stesso esempio in c++ (anche qui il goto è più veloce):
Le eccezioni NON si usano per uscire dai cicli!
kernel::panic
14-03-2008, 10:01
Le eccezioni NON si usano per uscire dai cicli!
Lo so (infatti è meglio che il mio capo non veda quel codice :D ), era solo di esempio...
Qui
Molto interessante, grazie! ;)
^TiGeRShArK^
14-03-2008, 10:10
Qui (http://www.microsoft.com/downloads/details.aspx?FamilyId=8C09FD61-3F26-4555-AE17-3121B4F51D4D&displaylang=en)
tnx :D
Nel frattempo quel linguaggio senza goto scritto da una scimmia (Python), mi ha fatto perdere una giornata di lavoro.
Eh si', e' troppo complesso dirmi che ho dimenticato di inizializzare una variabile a tempo di compilazione, o almeno inizializzarsela da solo... Me lo deve dire dopo tre ore di esecuzione e con un messaggio di errore che non c'entra nulla :)
Quanto amo Python... si' si'.
Nel frattempo quel linguaggio senza goto scritto da una scimmia (Python), mi ha fatto perdere una giornata di lavoro.
Eh si', e' troppo complesso dirmi che ho dimenticato di inizializzare una variabile a tempo di compilazione, o almeno inizializzarsela da solo... Me lo deve dire dopo tre ore di esecuzione e con un messaggio di errore che non c'entra nulla :)
Quanto amo Python... si' si'.
Se scrivevi i test per quel codice l'errore lo trovavi ben prima :O .
C'e' una tecnica di sviluppo chiamata Test Driven Development che e' una bomba per questo tipo di problemi, potresti farci un pensierino ;)
Si scherza eh ! :D :p :)
banryu79
14-03-2008, 14:48
Se scrivevi i test per quel codice l'errore lo trovavi ben prima :O .
C'e' una tecnica di sviluppo chiamata Test Driven Development che e' una bomba per questo tipo di problemi, potresti farci un pensierino ;)
A fek glielo vai a dire? Ma lol :asd:
^TiGeRShArK^
14-03-2008, 16:02
Se scrivevi i test per quel codice l'errore lo trovavi ben prima :O .
C'e' una tecnica di sviluppo chiamata Test Driven Development che e' una bomba per questo tipo di problemi, potresti farci un pensierino ;)
Si scherza eh ! :D :p :)
:asd:
secondo me dovrebbe prendere qualche lezione da settantunomilacentoquattro :O
:asd:
Se scrivevi i test per quel codice l'errore lo trovavi ben prima :O .
C'e' una tecnica di sviluppo chiamata Test Driven Development che e' una bomba per questo tipo di problemi, potresti farci un pensierino ;)
Mi dai un link che lo mando in giro qui? :D
DioBrando
14-03-2008, 19:05
Mi dai un link che lo mando in giro qui? :D
Paiton TìDìDì (http://powertwenty.com/kpd/downloads/TestDrivenDevelopmentInPython.pdf) :oink:
per il diveloper che non deve chiedere mai :asd:
:D
^TiGeRShArK^
14-03-2008, 20:02
ma solo a me da alla testa leggere cose del genere? :help:
if __name__=="__main__":
unittest.main()
odio gli underscore usati in quel modo :cry:
io odio gli underscore qualunque sia il motivo per cui vengono usati :asd:
cdimauro
14-03-2008, 21:10
Nel frattempo quel linguaggio senza goto scritto da una scimmia (Python), mi ha fatto perdere una giornata di lavoro.
Eh si', e' troppo complesso dirmi che ho dimenticato di inizializzare una variabile a tempo di compilazione, o almeno inizializzarsela da solo... Me lo deve dire dopo tre ore di esecuzione e con un messaggio di errore che non c'entra nulla :)
Quanto amo Python... si' si'.
Fran, ma almeno un check dei sorgenti dovresti farlo con PyCheck o tramite la comodissima iconcina che c'è in SPE: avresti avuto subito la segnalazione dell'uso di una variabile non inizializzata in precedenza. :O
Dì la verità: usi il notepad per lavorare con Python, vero? :p
P:S. Le variabili inizializzate da sole non mi piacciono: con quale valore dovrebbe essere fatto? Preferisco le ditine spezzate, così la prossima volta imparo a inizializzarle correttamente.
P.P.S. Come sempre: de gustibus. :)
ma solo a me da alla testa leggere cose del genere? :help:
if __name__=="__main__":
unittest.main()
odio gli underscore usati in quel modo :cry:
Una convenzione si doveva usare: in Python costruttori, distruttori, operatori, ecc. sono "first class functions". Essendo funzioni, al pari di qualunque altra, posso farci quello che voglio.
Esempio: posso usare dei mixin (apprò: mi sono fatto qualche giorno fa una comoda funzioncina per emularli, visto che Python non li supporta nativamente :O) che me li sovrascrivono, oppure conservo il vecchio valore, lo rimpiazzo col mio, ed eventualmente richiamo il vecchio codice quando voglio (questo modo di lavorare si chiama monkey patch, se non erro; un nome, una garanzia: vedi sopra :asd:).
In C++ o in altri linguaggi non puoi "mettere in frigo" un costruttore, sostituirlo con un altro, e tirare fuori il vecchio quando ti fa comodo. ;)
In C++ o in altri linguaggi non puoi "mettere in frigo" un costruttore, sostituirlo con un altro, e tirare fuori il vecchio quando ti fa comodo. ;)
E meno male :O
In C++ o in altri linguaggi non puoi "mettere in frigo" un costruttore, sostituirlo con un altro, e tirare fuori il vecchio quando ti fa comodo. ;)
a parte che è possibile attraverso un puntatore a funzione... ma per quale assurdo motivo dovrebbe essere utile? :fagiano: non sarebbe meglio avere due costruttori diversi e chiamare quello più adeguato a seconda dei casi? oppure avere un solo costruttore che capisce da solo in che caso si trova?
Fran, ma almeno un check dei sorgenti dovresti farlo con PyCheck o tramite la comodissima iconcina che c'è in SPE: avresti avuto subito la segnalazione dell'uso di una variabile non inizializzata in precedenza. :O
Dì la verità: usi il notepad per lavorare con Python, vero? :p
Uso Visual Studio, lo stesso tool che uso per scrivere in C++ e in C#. Non capisco perche' devo usare un tool diverso solo perche' il linguaggio e' fondamentalmente "pericoloso", per evitare di perdere ore. Ho perso una giornata su questa e solo per colpa delle scelte di design del linguaggio, non per colpa dei tool che avrei dovuto usare dei quali non conosco neppure l'esistenza. In C++/C#/Java non ne ho bisogno.
P:S. Le variabili inizializzate da sole non mi piacciono: con quale valore dovrebbe essere fatto? Preferisco le ditine spezzate, così la prossima volta imparo a inizializzarle correttamente.
Zero o stringa vuota.
P.P.S. Come sempre: de gustibus. :)
De gustibus? Una giornata di lavoro buttata nel bidet perche' il design del linguaggio e' fallato :)
In C++ o in altri linguaggi non puoi "mettere in frigo" un costruttore, sostituirlo con un altro, e tirare fuori il vecchio quando ti fa comodo. ;)
Grazie al cielo. Non rischio di perderci tutte le volte una giornata perche' il linguaggio decide di avvertirmi di un errore sintattico durante l'esecuzione, ore dopo.
Se prima sopportavo poco Python "a pelle", le ultime settimane che mi hanno costretto a lavorarci me lo hanno fatto sopportare sempre meno, ma con ottime motivazioni.
cdimauro
15-03-2008, 13:05
E meno male :O
a parte che è possibile attraverso un puntatore a funzione... ma per quale assurdo motivo dovrebbe essere utile? :fagiano: non sarebbe meglio avere due costruttori diversi e chiamare quello più adeguato a seconda dei casi? oppure avere un solo costruttore che capisce da solo in che caso si trova?
Il nocciolo della questione è che Python è un linguaggio dinamicamente tipato.
Quando scrivo a = b + c, b e c possono essere oggetti di qualunque tipo, e soltanto in fase di esecuzione "la matassa verrà sbrogliata".
Cosa vuol dire questo? Che se nel codice mi ritrovo pattern di codice che posso utilizzare per tipi che non necessariamente debbono essere "compatibili", ma che funzionalmente devono funzionare allo stesso modo, nulla m'impedisce di racchiudere il tutto in una funzione / costruttore / operatore, magari "ereditati" tramite un apposito mixin.
In soldoni: a me interessa modellare comportamenti.
Questo con un linguaggio staticamente tipato non è assolutamente realizzabile (e in ogni caso non è fattibile: non posso ricavare il puntatore di un operatore, ad esempio).
Uso Visual Studio, lo stesso tool che uso per scrivere in C++ e in C#. Non capisco perche' devo usare un tool diverso solo perche' il linguaggio e' fondamentalmente "pericoloso", per evitare di perdere ore. Ho perso una giornata su questa e solo per colpa delle scelte di design del linguaggio, non per colpa dei tool che avrei dovuto usare dei quali non conosco neppure l'esistenza. In C++/C#/Java non ne ho bisogno.
Zero o stringa vuota.
De gustibus? Una giornata di lavoro buttata nel bidet perche' il design del linguaggio e' fallato :)
Grazie al cielo. Non rischio di perderci tutte le volte una giornata perche' il linguaggio decide di avvertirmi di un errore sintattico durante l'esecuzione, ore dopo.
Se prima sopportavo poco Python "a pelle", le ultime settimane che mi hanno costretto a lavorarci me lo hanno fatto sopportare sempre meno, ma con ottime motivazioni.
Non è un errore sintattico, Fran: soltanto in fase di esecuzione puoi scoprire se QUELLA variabile esiste o meno, e questo non te lo può garantire nessun PyCheck o editor come SPE, che danno soltanto possibili indicazioni.
Esempio. Io posso avere un modulo (ma anche una classe) chiamato Pippo con soltanto questa funzione:
def Prova():
print a
che generarà il relativo warning.
Quindi sulla carta quel codice NON dovrebbe funzionare. Ma se scrivo questo:
import Pippo
Pippo.a = 5
Pippo.Prova()
il codice funzionerà in maniera impeccabile. :p
E casi come questi ce ne sono diversi (esempio: con le metaclassi posso generare automaticamente classi abbiano determinati "requisiti", ivi compresi la definizione di attribuiti / metodi che sulla classe di partenza non esistevano).
Dipende tutto da quel che si deve fare. La sintassi è corretta, e quando il sorgente viene compilato in bytecode, infatti, non viene generato nessun errore.
Sull'uso di valori di default, rientriamo nelle convenzioni: quelli che proponi sono i valori più papali e che, quindi, possono "risolvere" la maggior parte dei casi, ma davanti a = b / c con c non definita si ritorna al punto di partenza, ossia l'errore che ho commesso è stato quello di non definire (correttamente) la variabile prima di averla usata.
Tra l'altro l'uso di valori predefiniti porta a errori di mistyping difficilmente individuali (quando il codice, con un valore di default, non funziona lo stesso). ;)
Sugli editor/IDE nulla da dire, ma già in passato t'avevo avvisato di usarne qualcuno come SPE per evitare problemi come quelli dovuti all'indentazione necessaria in Python, ad esempio. :D
Sembra il Javascript, che tanto mi sta facendo penare in questo periodi perche' i problemi vengono fuori tutti a Runtime.
Peccato che per far partire l'applicazione e raggiungere il punto da testare ci si metta 40 secondi ogni volta, quando va bene.
// Pattern per la creazione di classe in javascript
function pippo()
{
}
//Decorator pattern per javascript
pippo.prototype.Prova = function()
{
alert(this.a);
}
//Usage
var pippoinstance=new pippo();
pippoinstance.a='Hello World';
pippoinstance.Prova();
Non proponetemi di fare una test before code qui perche' non ce ne si esce.
Tutto dipende da cosa si e' lanciato, eseguito o distrutto prima di lanciare
pippoinstance.Prova();
Non c'e' test che tenga.
Il problema qui e' che
this.a
puo' assumere valore "Undefined", che non e' un valore vero e' proprio.
Semplicemente e' lo stato che tiene conto del fatto che il campo non e' ancora stata dichiarata, e il tentativo di usarla genera un errore a runtime.
Diverso e' avere il valore "NULL", ovvero quando la variabile assume il valore null, che e' un valore come un altro. In questo caso non c'e' errore a Runtime.
Per fare le cose come si deve dovrei costringere tutte le funzioni a controllare l'esistenza di quanto usano, prima anche solo di valutarlo. A quel punto potrei usare i Pattern di Test, che altrimenti si arrabbierebbero subito.
Pero' cosi' facendo il codice diventerebbe decisamente piu' lungo, lento e illeggibile.
E' tanto piu' comodo essere "sicuri" che a Runtime la variabile di classe
this.a
esiste gia', perche' il compilatore ha gia' controllato tutto.
Mannaggia a me che ho accettato di entrare in questo progetto che era stato disegnato da un altro e che si e' licenziato. (Non che avessi molta scelta, comunque)
Dopo 5 mesi di lavoro su questo progetto la mia conclusione e' che il javascript non e' professionale.
Non consco Python ma spero non soffra degli stessi problemi o che almeno abbia i mezzi per poterli gestire.
cdimauro
15-03-2008, 15:39
Il comportamento è lo stesso, ma hai i mezzi per controllare l'esistenza di "attributi" (con la funzione bult-in hasattr) prima di usarli, oppure puoi usare la libreria di sistema unittest per gestire agevolmente batterie di test (che risolverebbe il problema alla radice :O ). ;)
Non è un errore sintattico, Fran: soltanto in fase di esecuzione puoi scoprire se QUELLA variabile esiste o meno, e questo non te lo può garantire nessun PyCheck o editor come SPE, che danno soltanto possibili indicazioni.
E' proprio questo il problema: non e' un errore sintattico, quindi l'errore nel mio codice spuntera' dopo ore, facendomi perdere una marea di tempo e andando contro il principio "Fail early, fail loud".
Esempio. Io posso avere un modulo (ma anche una classe) chiamato Pippo con soltanto questa funzione:
def Prova():
print a
che generarà il relativo warning.
Quindi sulla carta quel codice NON dovrebbe funzionare. Ma se scrivo questo:
import Pippo
Pippo.a = 5
Pippo.Prova()
il codice funzionerà in maniera impeccabile. :p
In altre parole un metodo e' sintatticamente corretto in base a chi lo invoca. Quanto lo odio :)
cdimauro
15-03-2008, 21:22
Fran, è un problema relativo a buona parte dei linguaggi "dinamici", Ruby compreso. :)
Lo si può risolvere in diversi modi, e uno fra questi è la TDD (sarebbe sufficiente coprire con un test ogni "biforcazione" del codice per avere la sicurezza di non essersi dimenticati di inizializzare correttamente tutte le variabili su cui lavora). :fiufiu:
Quanto al principio "Fail early, fail loud", se consideri che impieghi anche 1/10 del tempo a scrivere l'applicazione, vuol dire che puoi verificare molto prima se questa fallisce o meno coi dati reali.
Diciamo che un linguaggio "tradizionale" ti permette di applicare (velocemente) il principio sulla base della correttezza "sintattica" del codice, mentre con uno "dinamico" lo applichi ai dati.
Son cose diverse, ma l'obiettivo finale è arrivare alla correttezza dell'applicazione sulla base dei dati reali, e questo non viene a mancare. :)
Fran, è un problema relativo a buona parte dei linguaggi "dinamici", Ruby compreso. :)
Infatti c'e' un motivo per il quale non gradisco i linguaggi totalmente dinamici :)
Quanto al principio "Fail early, fail loud", se consideri che impieghi anche 1/10 del tempo a scrivere l'applicazione, vuol dire che puoi verificare molto prima se questa fallisce o meno coi dati reali.
Cesare, ti ricordo che il tempo impiegato a scrivere l'applicazione non e' solo il tempo impiegato a scrivere il codice, ma anche quello a testarlo e fare il debugging. Se un linguaggio mi costringe a ore di esecuzione per trovare un errore sintattico facilmente tracciabile prima dell'esecuzione, mi sta facendo perdere del tempo inutilmente per sola colpa di chi lo ha progettato. Senza se e senza ma.
Non ti ho fatto un esempio campato in aria: ho impiegato una giornata e mezza a scrivere tre righe di Python nel mondo reale su un progetto in produzione.
Poter aggiungere metodi e proprieta' e' una cosa utile in certe situazione, ma doverla pagare sempre e comunque anche quando non mi serve e' un errore di progettazione.
cdimauro
17-03-2008, 08:33
Non metto in dubbio che tu abbia perso tempo, ma i bug fanno parte della vita di un programmatore. :)
Quando ho cominciato a lavorare in Python, commettevo anch'io errori come quello, perché ero troppo abituato ai linguaggi "tradizionali" e al compilatore che ti segnalava l'assenza della dichiarazione di una variabile, perché è la sintassi stessa che lo richiede.
Con Python non si tratta di una questione sintattica, ma prettamente semantica...
Che sia grave non ci sono dubbi: infatti hai perso un bel po' di tempo per quella che ritieni una sciocchezza. Sciocchezze che, però, ritrovi anche in altri linguaggi che hanno una sintassi più "rigorosa":
int i; scanf("%d", i);
ma che ti portano a bug davvero subdoli da andare a individuare (mentre nel caso che t'è capitato dallo stack trace trovi immediatamente sia la causa dell'errore che la riga e colonna precisa).
Non è un caso che siano nati tool come "lint", o PyCheck, e per linguaggi completamente diversi...
Hai pagato un prezzo elevato per una sciochezza, ma per la mia esperienza il gioco vale la candela (ad esempio m'è capitato di realizzare un progetto in 20 giorni, quando lo stesso a un'altra società ha richiesto 6 mesi, e non so quanti c'abbiano lavorato), specialmente alla luce del fatto che una volta pronta l'applicazione la posso immediatamente testare con dati reali e rilevare, quindi, anche errori come quello che ti sono capitati.
Comunque questo http://cobra-language.com/ linguaggio che ha segnalato un utente qualche giorno fa è molto simile a Python, ma non ha i problemi di cui ti lamenti (unica eccezione, l'indentazione).
Ecco qui http://cobra-language.com/docs/python/ un confronto con Python.
Non metto in dubbio che tu abbia perso tempo, ma i bug fanno parte della vita di un programmatore. :)
Allora usiamo strumenti costruiti con i piedi, tanto i bug fanno parte della vita di un programmatore.
E' vero, ma strumenti migliori migliorano anche la vita. Python, per colpe di chi lo ha progettato si e' rivelato per me uno strumento peggiore su un progetto di grandi dimensioni.
Visto che gli errori alla guida fanno parte della vita, andiamo tutti in giro con una macchina con una ruota sgonfia :)
E cerchiamo di convincere gli altri che sia La Cosa Migliore Possibile (tm).
Con Python non si tratta di una questione sintattica, ma prettamente semantica...
Esatto. Un errore sintattico diventa un errore semantico per problemi di design e porta ad enormi perdite di tempo.
Che sia grave non ci sono dubbi: infatti hai perso un bel po' di tempo per quella che ritieni una sciocchezza. Sciocchezze che, però, ritrovi anche in altri linguaggi che hanno una sintassi più "rigorosa":
int i; scanf("%d", i);
Qui stai cambiando le carte in tavola :)
Il parallelo di quello che e' successo a me lo fai con questo codice:
scanf("%d", i);
Che ovviamente mi da' un errore di sintassi e non devo aspettare tre ore di esecuzione. Il design di Python trasforma un errore di sintassi in un bug subdolo. Questo e' un grosso problema dello strumento, non una mancanza del programmatore. Buoni strumenti limitano le possibilita' di errore a parita' di espressivita'. Sarebbe bastato, ad esempio, che come in Cobra potessi dichiarare un oggetto non aumentabile a run-time, da controllare staticamente, e senza modificare l'espressivita' del linguaggio avrebbe dato uno strumento piu' sicuro.
Hai pagato un prezzo elevato per una sciochezza, ma per la mia esperienza il gioco vale la candela
Nella mia esperienza e' valso un giorno e mezzo di lavoro perso per colpa di uno strumento inadeguato.
cdimauro
17-03-2008, 11:42
Non sto cambiando le carte in tavola, lo sai che non sono il tipo, Fran. :)
scanf non dà nessun errore sintattico, il codice viene compilato, e dio solo sa se e quando riuscirai a scoprire che mancava un & per passare il puntatore alla variabile anziché il suo valore. In ogni caso lo scopriresti a runtime. ;)
E tutto perché? Perché il C come linguaggio non supporta il passaggio per riferimento e passa tutto per valore (in ogni caso, anche se l'avesse avuto, con funzioni che accettano un numero di argomenti variabile, come scanf appunto, il problema sarebbe rimasto ugualmente).
E' sicuramente colpa di chi l'ha progettato, che ha trasformato un errore sintattico (che linguaggi come il Pascal risolvono con l'uso della keyword VAR nella definizione dell'elenco dei parametri di una procedura/funzione) in uno semantico... ;)
Sono d'accordo sull'uso degli strumenti migliori: lint per il C che ti fa scoprire quell'errore (semantico) con la scanf, e PyChecker per Python che fa saltare fuori la mancata dichiarazione di una variabile (meglio ancora SPE, che ha tutto integrato nell'IDE: Ctrl-Alt-C e il sorgente viene controllato semanticamente, oltre al controllo sintattico che di suo quest'IDE esegue in tempo reale mentre si sta scrivendo il codice).
Oggi come programmatori non possiamo affidarci esclusivamente al linguaggio, che è soltanto uno strumento: abbiamo la necessità di circondarci di diversi strumenti che concorrono a vario titolo alla produzione del codice finale. Non riesco a immaginare di lavorare in Java senza i comodi strumenti che IDE come Eclipse mettono a disposizione (tanto per fare un esempio con un linguaggio diverso da C e Python): la mia produttività ne risentirebbe sicuramente. :)
Non sto cambiando le carte in tavola, lo sai che non sono il tipo, Fran. :)
scanf non dà nessun errore sintattico, il codice viene compilato, e dio solo sa se e quando riuscirai a scoprire che mancava un & per passare il puntatore alla variabile anziché il suo valore. In ogni caso lo scopriresti a runtime. ;)
Cesare, non mi sono spiegato. L'equivalente in C++ del bug che mi ha creato problemi e' questo:
something = object.m_Member;
m_Member non dichiarato. Questo e' un errore sintattico. Se prendi un altro esempio, puoi dimostrare qualunque cosa e il suo contrario.
Oggi come programmatori non possiamo affidarci esclusivamente al linguaggio,
Sicuramente. Ma se per errori banali che devono essere trovati prima ancora di lanciare l'applicazione, il linguaggio impone (non permette) l'esecuzione, allora il linguaggio ha un gravissimo problema. In altri linguaggi questo non accade, pur supportando la stessa espressivita' di Python, quindi sono strumenti migliori.
cdimauro
17-03-2008, 13:09
Non avevo capito che ti riferissi al problema che hai avuto.
Ho soltanto portato un esempio di un costrutto sintatticamente corretto in C, ma che a livello semantico genera problemi. Tutto qui.
Non avevo capito che ti riferissi al problema che hai avuto.
Ho soltanto portato un esempio di un costrutto sintatticamente corretto in C, ma che a livello semantico genera problemi. Tutto qui.
Quanti ne vuoi di esempi uguali in C++? :D
Il mio discorso si basa sul fatto che una cosa fondamentale come la presenza di una variable in un oggetto (dal quale non ho bisogno alcun comportamento dinamico) non sia validata a tempo di compilazione. Figurati che voglio usare un qualche tool che me la validi mentre scrivo il codice, per questo preferisco C#/Java a C++.
Mentre Python mi impone come design del linguaggio di pagare il prezzo di un oggetto dinamico anche quando questa feature non mi serve. Dai un'occhiata a Corba, non derivasse da Python sarebbe un gran linguaggio :D
A parte gli scherzi, unit testing e design by contract direttamente nel linguaggio, compila per .NET, sintassi pulita, forse un po' troppy Python-like (indentazione... grrrr), tipizzazione statica o dinamica a scelta. E' un linguaggio con un design chiaramente superiore a Python.
cdimauro
17-03-2008, 13:26
Proprio per questo l'ho segnalato. :)
Ha certi aspetti come lo unit testing e il design-by-contract che mi affascinano da sempre (anche la scelta fra tipizzazione statica o dinamica è interessante, ma poi ho visto gli esempi coi generic e mi sono cadute le braccia: è troppo comodo avere un tipo "generico" e... usarlo subito, come faccio adesso). Vedremo come si evolverà, perché promette bene.
Un'altra cosa che forse non hai notato è che non richiede l'indicazione di self come primo parametro nella definizione dei metodi e, per accedere alle variabili di istanza (o di classe, se non ricordo male) è sufficiente premettere il punto (es: .x = 0); e... non usa i due punti alla fine di un costrutto di definizione o controllo.
Mi sa che l'unica cosa che ti farà desistere dal provarlo rimane l'indentazione forzata... :p
Proprio per questo l'ho segnalato. :)
Ha certi aspetti come lo unit testing e il design-by-contract che mi affascinano da sempre (anche la scelta fra tipizzazione statica o dinamica è interessante, ma poi ho visto gli esempi coi generic e mi sono cadute le braccia: è troppo comodo avere un tipo "generico" e... usarlo subito, come faccio adesso). Vedremo come si evolverà, perché promette bene.
Un'altra cosa che forse non hai notato è che non richiede l'indicazione di self come primo parametro nella definizione dei metodi e, per accedere alle variabili di istanza (o di classe, se non ricordo male) è sufficiente premettere il punto (es: .x = 0); e... non usa i due punti alla fine di un costrutto di definizione o controllo.
Mi sa che l'unica cosa che ti farà desistere dal provarlo rimane l'indentazione forzata... :p
L'ho scaricato invece!
Ma mi sembra molto acerbo, non c'e' integrazione con VS2005/2008 e non ho capito come creare un oggetto da consumare in .NET. Appena mi sistemano queste due cosette lo provo piu' seriamente. DbC e Unit Testing nel linguaggio mi intrigano moltissimo.
cdimauro
17-03-2008, 14:17
L'ho scaricato invece!
Ma mi sembra molto acerbo, non c'e' integrazione con VS2005/2008 e non ho capito come creare un oggetto da consumare in .NET. Appena mi sistemano queste due cosette lo provo piu' seriamente. DbC e Unit Testing nel linguaggio mi intrigano moltissimo.
:eek: Se riesci a cavarci qualcosa fammi sapere, che sarei interessato ad approfondire se ne valesse la pena. :)
Ahah
Guardate qui, giusto oggi.
http://www.hwupgrade.it/forum/showthread.php?t=1703005
cdimauro
17-03-2008, 16:24
ROTFL :rotfl: :rotfl: :rotfl: Manco a farlo apposta! Un'altra vittima della semantica... :asd:
Sto tempestando il tipo di Cobra adesso. E' gentilissimo, mi ha spiegato come creare oggetti .NET invece di eseguibili. E mi ha detto che sta lavorando sull'integrazione in VS2005/VS2008.
Se qualcuno vuole dargli una mano lo contatti :)
kernel::panic
17-03-2008, 18:16
Sto tempestando il tipo di Cobra adesso.
Poveretto, maledirà il giorno in cui ho postato il link su questo forum!! :D :D
Scherzi a parte penso sia molto contento di trovare gente interessata al suo linguaggio, anche se così nuovo.
Il link a Cobra (e anche ad altri linguaggi) l'ho trovato in questa pagina di Mono... se può interessare:
http://www.mono-project.com/Languages
Ciao ;)
cdimauro
17-03-2008, 19:47
Al momento l'unica cosa che posso fare per dargli una mano è la cavia, ma prima devo avere abbastanza tempo per studiarmi bene la sintassi del linguaggio (e focalizzare le differenze con Python, a cui ormai sono assuefatto :p).
DioBrando
18-03-2008, 00:13
Mi sembrava di averne già sentito parlare...
ed in effetti poi ho ripescato un articolo piuttosto recente proprio su Cobra (http://programmazione.it/index.php?entity=eitem&idItem=38633)
banryu79
18-03-2008, 09:51
Scusate, ma in Cobra c'è il goto? :p
cdimauro
18-03-2008, 09:52
In Cobra quello che fottutamente manca è la documentazione... :muro: :muro: :muro:
<!TAG STYLE_ERROR>ERROR: <type 'exceptions.KeyError'> ('SwappableModel',) D:\devXXXX\EngineLevelSceneBuilder.py(553)<!TAG STYLE_NORMAL>
<!TAG STYLE_ERROR>ERROR: Failed building export_xbox360\XXXX.engine_level_scene<!TAG STYLE_NORMAL>
Errore di sintassi due settimane dopo l'aver scritto il codice. Come fai a non amare questo linguaggio? :D
cdimauro
25-03-2008, 16:11
Ehi, aspetta, quello è un KeyError!
C'è una chiave NON presente in quel dizionario, e stai cercando di accedervi!!
Questo è un problema di dati!!! :)
Comunque adesso devo proprio scappare che il piccolo è scatenato e m'hanno chiamato per dare una mano. :D
Ehi, aspetta, quello è un KeyError!
C'è una chiave NON presente in quel dizionario, e stai cercando di accedervi!!
Questo è un problema di dati!!! :)
Comunque adesso devo proprio scappare che il piccolo è scatenato e m'hanno chiamato per dare una mano. :D
Figo, e io volevo solo una struttura :D
Adoro questo linguaggio.
Figo, e io volevo solo una struttura :D
Adoro questo linguaggio.
Se vuoi una struttura, meglio un oggetto che un dizionario.
In realta' neanche con gli oggetti hai la garanzia in generale che i campi ci siano, ma basta definirti un costruttore con argomenti e sei a posto
class MyStruct:
def __init__(self,field1,field2,field3...):
self.field1 = field1
self.field2 = field2
# ...
se poi sei pigro, usi molte strutture e ti rompe definire ogni volta una struttura opportuna, allora fattorizzi tutto in una funzione di comodo:
def newStruct( name, *fields ):
import new
import compiler
header = 'def constructor( self, %s ):\n ' % ','.join( fields )
body = '\n '.join([ "self.%s = %s" % (x,x) for x in fields ])
source = header + body
exec source
return new.classobj(name, () , {'__init__' : constructor} )
Da usare cosi'
>>> MyStruct = newStruct('MyStruct','uno','due','tre')
>>> x = MyStruct()
Traceback (most recent call last):
File "<stdin>", line 1, in ?
TypeError: constructor() takes exactly 4 arguments (1 given)
>>> x = MyStruct( uno = 1, due=2, tre=3 )
>>> x.uno
1
:D :p
(ovviamente la funzione va sistemata, perche' c'e' un exec con argomenti non controllati, ma penso renda l'idea )
Scusate...vado a rimettere la cena :Puke:
Scusate...vado a rimettere la cena :Puke:
Ho trovato la soluzione ai miei problemi con Python.
Riscrivo il generatore di shader in C#.
||ElChE||88
25-03-2008, 22:44
def newStruct( name, *fields ):
import new
import compiler
header = 'def constructor( self, %s ):\n ' % ','.join( fields )
body = '\n '.join([ "self.%s = %s" % (x,x) for x in fields ])
source = header + body
exec source
return new.classobj(name, () , {'__init__' : constructor} )
E' più presentabile in aramaico antico. :asd:
E' più presentabile in aramaico antico. :asd:
Come sei tronfio :D
Ho trovato la soluzione ai miei problemi con Python.
Mamma mia non lo sopporto, mi provoca l'orticaria solo a guardarlo per sbaglio.
Riscrivo il generatore di shader in C#.
Ottima soluzione :asd:
||ElChE||88
25-03-2008, 22:57
Come sei tronfio :D
Questa frase non mi è nuova. :asd:
Ho trovato la soluzione ai miei problemi con Python.
Riscrivo il generatore di shader in C#.
Quanto è complicato un generatore di shader? :fagiano:
Ho trovato la soluzione ai miei problemi con Python.
Riscrivo il generatore di shader in C#.
a ognuno il suo. Io trovo invece che sia il C# ad essere troppo complicato (soprattutto con le varie aggiunte fatte nel corso del tempo), fa' un po' tu :boh:
DioBrando
25-03-2008, 23:07
Come sei tronfio :D
Mamma mia non lo sopporto, mi provoca l'orticaria solo a guardarlo per sbaglio.
Ottima soluzione :asd:
razzisti :cry:
d'altra parte da uno giuentino e un interista non è che ci possa aspettare di meglio...:asd:
:D
E alla faccia vostra mi sono iscritto alla PyCon2 :O magari ci saranno delle track proprio gaming-oriented...
Dai chi mi fa compagnia? :flower:
cdimauro
26-03-2008, 07:36
Figo, e io volevo solo una struttura :D
Adoro questo linguaggio.
Le struct non esistono (in realtà esistono, ma servono ad altro :D): puoi creare una classe apposita che, tramite il costruttore, definisce gli attributi / variabili d'istanza che ti serve siano presenti; come suggeriva anche Marco.
Concettualmente è simile a quanto faresti con C++, C#, Java, ecc.
Comunque coi dizionari finora non ho mai avuto la necessità di crearmi una "struct", per cui la strada che hai intrapreso con quel pezzo di codice molto probabilmente è quella giusta.
Se ci dici esattamente a cosa ti serviva, ti possiamo dare una mano per risolvere il tuo problema. :flower:
x DioBrando: diavolo tentatore! Mi sa che finirò per cadere nella trappola. :p
Quanto è complicato un generatore di shader? :fagiano:
Come per tutte le cose, sapendo quello che si sta facendo non e' complicatissimo. Il problema e' che fino a un paio di anni fa nessuno al mondo sapeva, di preciso, come scrivere un generatore di shader perche' era un problema nuovo :D
Dopo due anni di esperienza a lavorarci sopra posso tagliare qualche angolo, semplificare qui e la', fare qualche assunzione e, usando un linguaggio degno di questo nome, probabilmente si riesce a riscrivere quell'accozzaglia in maniera molto piu' semplice.
a ognuno il suo. Io trovo invece che sia il C# ad essere troppo complicato (soprattutto con le varie aggiunte fatte nel corso del tempo), fa' un po' tu :boh:
Ti capisco, d'altronde Python e' pseudocodice leggibile. Tipo questo:
def newStruct( name, *fields ):
import new
import compiler
header = 'def constructor( self, %s ):\n ' % ','.join( fields )
body = '\n '.join([ "self.%s = %s" % (x,x) for x in fields ])
source = header + body
exec source
return new.classobj(name, () , {'__init__' : constructor} )
Si legge come fosse inglese :D
Comunque coi dizionari finora non ho mai avuto la necessità di crearmi una "struct", per cui la strada che hai intrapreso con quel pezzo di codice molto probabilmente è quella giusta.
Cesare, perdere due giornate di lavoro per un errore di sintassi e trovarmi un altro errore come questo due settimane dopo il deploy impazzendo per capire di che cosa si tratta, non e' cio' che definisco intraprendere una strada giusta.
Comunque non ho scritto io quel codice. Io non scrivo in Python, ci ho solo dovuto mettere le mani... e non lo faccio piu'.
Le struct non esistono (in realtà esistono, ma servono ad altro :D)
:eekk: non fa una grinza :asd:
cdimauro
26-03-2008, 09:52
Come per tutte le cose, sapendo quello che si sta facendo non e' complicatissimo. Il problema e' che fino a un paio di anni fa nessuno al mondo sapeva, di preciso, come scrivere un generatore di shader perche' era un problema nuovo :D
Dopo due anni di esperienza a lavorarci sopra posso tagliare qualche angolo, semplificare qui e la', fare qualche assunzione e, usando un linguaggio degno di questo nome, probabilmente si riesce a riscrivere quell'accozzaglia in maniera molto piu' semplice.
Non è un problema di linguaggio questa volta. ;)
Ti capisco, d'altronde Python e' pseudocodice leggibile. Tipo questo:
def newStruct( name, *fields ):
import new
import compiler
header = 'def constructor( self, %s ):\n ' % ','.join( fields )
body = '\n '.join([ "self.%s = %s" % (x,x) for x in fields ])
source = header + body
exec source
return new.classobj(name, () , {'__init__' : constructor} )
Si legge come fosse inglese :D
E' una soluzione "universale" al problema di creare una struttura qualunque. Cosa non fattibile con altri linguaggi, comunque.
Per creare strutture "as usual":
class Punto:
def __init__(self, x, y):
self.x = x
self.y = y
p = Punto(0, 0)
print p.x, p.y
p.x = 1
p.y = 2
print p.x, p.y
Cosa c'è di "illegibile" in questo? ;)
Cesare, perdere due giornate di lavoro per un errore di sintassi e trovarmi un altro errore come questo due settimane dopo il deploy impazzendo per capire di che cosa si tratta, non e' cio' che definisco intraprendere una strada giusta.
Quest'errore l'avresti commesso anche in C#, col quale vorresti riscriverlo. Da qui http://support.microsoft.com/kb/309357 :
/Use the indexer of the Hashtable class to retrieve your objects. The indexer takes
//Key as a parameter and accesses it with the Hashed location.
try
{
MessageBox.Show(MyTable[Person1.Lname].ToString());
MessageBox.Show(MyTable[Person2.Lname].ToString());
MessageBox.Show(MyTable[Person3.Lname].ToString());
}
catch (NullReferenceException ex)
{
MessageBox.Show("Key not in Hashtable");
MessageBox.Show(ex.Message);
Prova a togliere il try/catch che intercetta l'eccezione (di chiave non presente): la situazione sarebbe esattamente la stessa del codice Python di cui ti lamenti. :p
Comunque non ho scritto io quel codice. Io non scrivo in Python, ci ho solo dovuto mettere le mani... e non lo faccio piu'.
Infatti il problema è proprio che non hai scritto tu quel codice, e chi l'ha fatto non mi sembra particolarmente ferrato con Python e, dopo tutti i disastri che finora hai riportato, nemmeno col testing del codice. :)
:eekk: non fa una grinza :asd:
Già, perché si usano per leggere (e scrivere) strutture di dati da file.
Python non ha bisogno del classico concetto di struct che si trova in C o in altri linguaggi: ci sono le classi oppure i dizionari per questo. ;)
E' una soluzione "universale" al problema di creare una struttura qualunque. Cosa non fattibile con altri linguaggi, comunque.
Per fortuna in altri linguaggi non e' facile scrivere quegli orrori :)
Quest'errore l'avresti commesso anche in C#, col quale vorresti riscriverlo. Da qui http://support.microsoft.com/kb/309357 :
No Cesare, in C# userei qualcosa che mi fa' un bell'errore in fase di compilazione se commetto quella fesseria. Non scomodo certo una hash table.
Python non ha bisogno del classico concetto di struct che si trova in C o in altri linguaggi: ci sono le classi oppure i dizionari per questo. ;)
E ci sono tanti linguaggio molto piu' robusti che mi fanno perdere meno tempo ;)
cdimauro
26-03-2008, 12:34
Quindi il problema è la mancanza di costrutto struct-like del C? Voglio dire: in un linguaggio come il C# la soluzione al tuo problema sarebbe stata quella di usare una "struct"?
Rimane, comunque, il fatto che l'autore del codice non mi sembra particolarmente ferrato con Python e il testing in generale. ;)
Quindi il problema è la mancanza di costrutto struct-like del C? Voglio dire: in un linguaggio come il C# la soluzione al tuo problema sarebbe stata quella di usare una "struct"?
Rimane, comunque, il fatto che l'autore del codice non mi sembra particolarmente ferrato con Python e il testing in generale. ;)
Cesare, io ti dico "Per colpa di questo ho perso due giorni di lavoro che usando un altro linguaggio non avrei perso" e tu mi rispondi "L'autore non e' ferrato in Python". In pratica mi stai dicendo che se il programmatore non e' ferrato in Python, rischia di scrivere codice che fa perdere tantissimo tempo. La stessa cosa che accade in C, anzi, peggio :)
cdimauro
26-03-2008, 12:57
Mi sembra normale parlare di "ferratezza": un dizionario/hashtable è un oggetto che ha dei PRECISI requisiti d'utilizzo.
Se cerchi di accedere a un elemento inesistente Python solleva un'eccezione.
Se utilizzi un dizionario senza conoscere questo "dettaglio" non di poco conto oppure con leggerezza, commetti un errore, come quello che hai mostrato e che t'ha fatto perdere.
Ma è una cosa che capita con altri linguaggi appunto.
Tra l'altro i dizionari permettono di evitare il sollevamento dell'eccezione restituendo un valore di default.
In entrambi i casi, quindi, bisogna conoscere lo strumento. Ecco perché dico che bisogna essere ferrati. :)
Detto ciò, mi sembra di capire che per risolvere il tuo problema sarebbe bastato una struct.
Ne prendo atto, ma in Python lo si può fare:
- in maniera MOLTO simile (vedi l'esempio che t'ho fornito prima);
- coi dizionari, usandoli in maniera appropriata.
Questo senza considerare che una buona unittest avrebbe permesso di risalire al bug prima ancora di lanciare l'esecuzione dello script. ;)
Mi sembra normale parlare di "ferratezza": un dizionario/hashtable è un oggetto che ha dei PRECISI requisiti d'utilizzo.
Se cerchi di accedere a un elemento inesistente Python solleva un'eccezione.
Se utilizzi un dizionario senza conoscere questo "dettaglio" non di poco conto oppure con leggerezza, commetti un errore, come quello che hai mostrato e che t'ha fatto perdere.
Ma io non voglio usare una hash table e non voglio conoscere quel dettaglio per qualcosa che puo' essere risolto in maniera molto piu' semplice con un linguaggio diverso.
Io qui non sto imparando un linguaggio, io qui sto finendo un gioco, e con una previsione di 1000/2000 bug da fissare da qui ai prossimi quattro mesi, francamente, con dettagli delle hash table di Python mi ci sciacquo ;)
Se per ogni fix dovessi andarmi a studiare le sottigliezze del linguaggio per evitare di cadere nelle sue trappole, il gioco esce nel 2050.
Mi ha fatto perdere tempo che non avrei perso con un linguaggio migliore, e' l'unica cosa che mi interessa.
Ma è una cosa che capita con altri linguaggi appunto.
Questo no perche' in altri linguaggi ho a disposizione strumenti piu' robusti.
Questo senza considerare che una buona unittest avrebbe permesso di risalire al bug prima ancora di lanciare l'esecuzione dello script. ;)
E se mia nonna aveva le ruote era un carretto, e se fossimo tutti piu' buoni non ci sarebbero guerre...
Non mi interessa quello che poteva essere, mi interessa quello che e' accaduto: due giorni persi perche' lo strumento che hanno scelto e' inadeguato grrrr.
cdimauro
26-03-2008, 13:14
Lo strumento giusto era questo:
class Punto:
def __init__(self, x, y):
self.x = x
self.y = y
p = Punto(0, 0)
print p.x, p.y
p.x = 1
p.y = 2
print p.x, p.y
;)
Lo strumento giusto era questo:
class Punto:
def __init__(self, x, y):
self.x = x
self.y = y
p = Punto(0, 0)
print p.x, p.y
p.x = 1
p.y = 2
print p.x, p.y
;)
Bene. Ora manda una mail al tipo di Python e digli che se sbaglio cosi' platealmente ad usare lo strumento giusto mi dovrebbe avvertire presto. Non due settimane dopo il deploy di quel codice :D
Anzi no, uso un linguaggio serio appena mi sono smazzato sti 2000 bug...
cdimauro
26-03-2008, 13:33
Fran, ma il codice l'hai scritto tu o qualche tuo collega? Nel primo caso sei giustificato: odi Python, e non hai mai mostrato interesse a impararlo. :p
Comunque il creatore di Python lavora per la "concorrenza" ( www.google.com ). :fiufiu:
P.S. Se non ti piacciono i pitoni, puoi provare coi cobra. :stordita:
Fran, ma il codice l'hai scritto tu o qualche tuo collega? Nel primo caso sei giustificato: odi Python, e non hai mai mostrato interesse a impararlo. :p
Io imparo qualunque cosa mi serva per andare prima a casa, non ho pregiudizi su nulla ;)
Ricapitolo la storia:
- Qualcuno ha avuto l'imponente idea di usare Python per scrivere il nostro sistema di build degli asset
- Io ho avuto la sfortuna di dover aggiungere un flag per una risorsa
- Due righe di codice che ho dovuto aggiungere si sono trasformate nell'inferno che ti ho descritto
Tutto il lavoro avrebbe dovuto prender trenta o quaranta secondi al massimo, due settimane dopo sono ancora qui che debuggo... Anzi no, se lo sta debuggando quello che ha scelto Python ora... Ah l'ironia della sorte :D
Tutto il lavoro avrebbe dovuto prender trenta o quaranta secondi al massimo, due settimane dopo sono ancora qui che debuggo... Anzi no, se lo sta debuggando quello che ha scelto Python ora... Ah l'ironia della sorte :D
E che dice...per curiosità ? Sta cominciando a pensare di aver sbagliato scelta ?
cdimauro
26-03-2008, 14:10
Io imparo qualunque cosa mi serva per andare prima a casa, non ho pregiudizi su nulla ;)
Ricapitolo la storia:
- Qualcuno ha avuto l'imponente idea di usare Python per scrivere il nostro sistema di build degli asset
- Io ho avuto la sfortuna di dover aggiungere un flag per una risorsa
- Due righe di codice che ho dovuto aggiungere si sono trasformate nell'inferno che ti ho descritto
Tutto il lavoro avrebbe dovuto prender trenta o quaranta secondi al massimo, due settimane dopo sono ancora qui che debuggo... Anzi no, se lo sta debuggando quello che ha scelto Python ora... Ah l'ironia della sorte :D
Visto? Hai appena dimostrato che dio esiste (ed è giusto, anzi: vendicativo :asd:)... :p
DioBrando
26-03-2008, 14:39
Visto? Hai appena dimostrato che dio esiste (ed è giusto, anzi: vendicativo :asd:)... :p
:asd:
cmq se uno "sperimenta" l'utilizzo del linguaggio per scrivere tutto il sistema di build di un progetto così imponente senza aver almeno testato prima se è quello che fa per lui o meno, non fa una mossa esattamente geniale.
A prescindere dallo strumento scelto.
E che dice...per curiosità ? Sta cominciando a pensare di aver sbagliato scelta ?
Cambiamo argomento :D
:asd:
cmq se uno "sperimenta" l'utilizzo del linguaggio per scrivere tutto il sistema di build di un progetto così imponente senza aver almeno testato prima se è quello che fa per lui o meno, non fa una mossa esattamente geniale.
A prescindere dallo strumento scelto.
Cambiamo argomento :D
mindwings
26-03-2008, 18:00
Cambiamo argomento :D
si infatti fornisco l'input
http://www.st.cs.uni-sb.de/edu/seminare/2005/advanced-fp/docs/sweeny.pdf
cosa ne pensi dell'opinione di un tuo "collega" :D
In generale nel futuro utilizzeremo i linguaggi fuzionali :confused:
||ElChE||88
26-03-2008, 18:32
si infatti fornisco l'input
http://www.st.cs.uni-sb.de/edu/seminare/2005/advanced-fp/docs/sweeny.pdf
cosa ne pensi dell'opinione di un tuo "collega" :D
Dal pdf:
By 2009, game developers will face...
CPU's with:
- 20+ cores
:asd: :asd: :asd:
DioBrando
27-03-2008, 01:31
Cambiamo argomento :D
almeno rassicuraci sul fatto che questa persona sia ancora (almeno per il momento) sana e provvista di tutti i suoi arti :asd:
si infatti fornisco l'input
http://www.st.cs.uni-sb.de/edu/seminare/2005/advanced-fp/docs/sweeny.pdf
cosa ne pensi dell'opinione di un tuo "collega" :D
In generale nel futuro utilizzeremo i linguaggi fuzionali :confused:
Personalmente io trovo interessanti alcune annotazioni.
1) Prima di tutto, le slide 27/29 ci mostrano una situazione piuttosto similare a quella che è capitata a fek, ovvero dei mancati warning da parte del sistema in fase di compilazione.
"Reliability
Or:
If the compiler doesn’t beep,
my program should work", una sorta di principio silenzio assenso :D
2) Memory model
– Garbage collection should be the only option: questo a riprova di tutti i discorsi che si fanno ciclicamente sulla bontà nello scegliere linguaggi come Java o C# per iniziare a programmare ma non solo, anche come investimento per un futuro lavorativo
3) Effects Model
§ Purely Functional is the right default
§ Imperative constructs are vital features
that must be exposed through explicit
effects-typing constructs:
questo invece è il punto che mi intriga di più e che si ricollega a quel che ha scritto mindwings.
Leggendo il trafiletto mi sono tornati alla mente recenti discussioni riguardo la strada intrapresa da Microsoft nello sviluppo di F#, DLR e della necessità di convergere verso una maggiore efficienza in ambienti in cui l'esecuzione sarà giocoforza concorrente.
E sono poi alla fin fine le necessità esposte in quelle slide, + o -...
Linko i vari articoli a cui mi riferisco, casomai ve li foste persi:
1 (http://programmazione.it/index.php?entity=eitem&idItem=38469)
2 (http://msdn2.microsoft.com/it-it/magazine/cc164244.aspx)
3 (http://blogs.devleap.com/marco/archive/2007/11/01/f-diventa-un-prodotto.aspx)
4 (http://www.onevista.it/08/11/2007/f-il-nuovo-linguaggio-net-e-funzionale/)
Sul sito ufficiale del Lang.NET Symposium trovate video e slide (e consiglio di darci un'occhiata in generale).
Citazione:
For example, it is quite common to have conditionals THAT DO NOT NEST.
In which case you have two possibilities
- use goto, and be happy, since it doesn't enforce nesting
This makes the code _more_ readable, since the code just does what
the algorithm says it should do.
- duplicate the code, and rewrite it in a nesting form so that you can
use the structured jumps.
This often makes the code much LESS readable, harder to maintain,
and bigger.
The Pascal language is a prime example of the latter problem. Because it
doesn't have a "break" statement, loops in (traditional) Pascal end up
often looking like total shit, because you have to add totally arbitrary
logic to say "I'm done now".
Dal pdf:
By 2009, game developers will face...
CPU's with:
- 20+ cores
:asd: :asd: :asd:
Se era solo per la tecnica magari aveva ragione... Purtroppo di mezzo ci sta sempre il marketing... :asd:
Gia' adesso si possono comperare macchine ad 8 core (il Mac Pro ad esempio). Non mi sembra cosi' impossibile come previsione...
^TiGeRShArK^
27-03-2008, 16:17
Gia' adesso si possono comperare macchine ad 8 core (il Mac Pro ad esempio). Non mi sembra cosi' impossibile come previsione...
beh..
lì a quanto ho capito stava parlando di console...
Cmq il mac pro non è venduto ad un prezzo diciamo "popolare" :asd:
costa circa 4 volte la mia workstation con un quad (2.4@3.0 :p) :mbe:
almeno rassicuraci sul fatto che questa persona sia ancora (almeno per il momento) sana e provvista di tutti i suoi arti :asd:
E' ben protetto.
Comunque si usano gia' linguaggi funzionali per fare videogiochi gia' da un paio d'anni a questa parte (Python, LUA...).
DioBrando
27-03-2008, 16:43
E' ben protetto.
Comunque si usano gia' linguaggi funzionali per fare videogiochi gia' da un paio d'anni a questa parte (Python, LUA...).
Sì lo sò, ma sono rimasto un po' sorpreso dalle dichiarazioni piuttosto nette di Heijlsberg riguardo all'evoluzione futura dei linguaggi (sia per quanto riguarda il design che la loro adozione).
Anche se in realtà la direzione non è quella del paradigma funzionale puro ma di linguaggi ibridi o che possono essere utilizzati come tali (Python, Ryby, Perl...), mi chiedevo per esempio in questo quadro come si colloca il percorso di Java.
E non è una boutade quella di Hejlsberg, è dalla presentazione di C# 3.0 che lo sta ripetendo (non solo lui in realtà...); quindi è evidente che sia una riflessione ben meditata.
E quindi mi sarebbe piaciuto anche sentire il vostro parere...
mindwings
27-03-2008, 17:03
altra carne :D
http://steve-yegge.blogspot.com/2007/02/next-big-language.html
beh..
lì a quanto ho capito stava parlando di console...
Cmq il mac pro non è venduto ad un prezzo diciamo "popolare" :asd:
costa circa 4 volte la mia workstation con un quad (2.4@3.0 :p) :mbe:
By 2009, game developers will face...
Si parla di sviluppatori di giochi, non di utenti finali. Nell'ipotesi di tre anni di sviluppo vuol dire che l'anno prossimo gli sviluppatori dovranno tenere a mente le macchine del 2012. Ripeto: non mi sembra affatto fantascienza.
^TiGeRShArK^
27-03-2008, 18:27
Si parla di sviluppatori di giochi, non di utenti finali. Nell'ipotesi di tre anni di sviluppo vuol dire che l'anno prossimo gli sviluppatori dovranno tenere a mente le macchine del 2012. Ripeto: non mi sembra affatto fantascienza.
si..
ma là parlava esplicitamente del 2009, non del 2012 :p
Anzi, per essere esatti delle "console next-gen" del 2009.
Per me potranno benissimo avere 20 e + core.
Ma altrettanto non direi dei PC o MAC del 2009 :p
Eh va bhè, pure Bill Gates prevedeva che i 640K erano sufficienti per tutti. Capita di prendere cantonate quando si ragiona solo in termini tecnici, purtroppo.
mindwings
27-03-2008, 19:04
le slides a parte quel dettaglio parlano di altra roba:fagiano:
DioBrando
27-03-2008, 19:53
altra carne :D
http://steve-yegge.blogspot.com/2007/02/next-big-language.html
ho letto sommariamente ma quando ho sfogliato un po' di requisiti la mia reazione è stata: "poi? nient'altro? Una fettina di :ciapet: no?"
:D
Sono interessanti anche i commenti, seppur, dopo aver visto i primi in cui veniva richiamato l'esempio di JavaScript come linguaggio che rispondesse meglio ai bisogno espressi dall'autore, mi sia venuta una discreta voglia di chiudere :stordita:
Eh va bhè, pure Bill Gates prevedeva che i 640K erano sufficienti per tutti. Capita di prendere cantonate quando si ragiona solo in termini tecnici, purtroppo.
Non l'ha mai proferita, gli è stata erroneamente attribuita.
le slides a parte quel dettaglio parlano di altra roba:fagiano:
Sì, come ho detto il richiamo ai linguaggi funzionali mi interessava nella prospettiva di evoluzione futura e volevo sapere la vostra opinione.
Molto è stato scritto sui benefici dell'utilizzo del paradigma OO (e anche da questo trae la sua forza Java, al di là della bontà o meno della piattaforma).
Ma in questa luce e sugli investimenti che la MS sta facendo in merito a F#, DLR che coinvolge i vari IronPython e IronRuby (ma non solo dato che si parla di Silverlight per PHP), mi domando se si debba ripensare in qualche modo questo approccio un po' "talebano" della metodologia OO.
Raccogliendo i pezzi mi sembra che in realtà molti si muovano in questa direzione: Sun stessa con il rilascio di JavaFX (che và a colmare l'assenza di un contraltare per Silverlight) propone il relativo linguaggio di scripting che non è però affatto OO, ma è più simile ad linguaggio procedurale.
Lo stesso Groovy consente uno stile di programmazione funzionale ed infatti ha mutuato caratteristiche di buona parte dei linguaggi dinamicamente tipati come Python e Ruby.
Insomma ragionandoci su, forse, dico forse, la prospettiva annunciata da Hejlsberg&soci la stiamo già vivendo solo mi fa un po' specie vedere pronunciate parole così secche e nette, dopo anni quasi di indottrinamento sull'OOP.
Originariamente inviato da mjordan
Eh va bhè, pure Bill Gates prevedeva che i 640K erano sufficienti per tutti. Capita di prendere cantonate quando si ragiona solo in termini tecnici, purtroppo.
Non l'ha mai proferita, gli è stata erroneamente attribuita.
Non lo sapevo dell'errata attribuzione, ho cercato un po' in giro e sembra tu abbia ragione.
Bill Gates l'ha smentita nel 1996 durante un'intervista.
PEccato pero' che la frase l'avrebbe detta nel 1981.
L'ha smentita 15 anni dopo? Mi sa che e' un po' tardino... gatta ci cova.
Comunque che ne poteva il povero Gates allora?
Ha ereditato la architettura Intel 8086, e se l'e' tenuta cosi' come'era.
Avrebbe anche potuto pestare i piedi e piangere ma, allora, dubito che alla Intel l'avrebbero ascoltato. Oggi forse invece...
cdimauro
27-03-2008, 21:34
Non lo sapevo dell'errata attribuzione, ho cercato un po' in giro e sembra tu abbia ragione.
Bill Gates l'ha smentita nel 1996 durante un'intervista.
PEccato pero' che la frase l'avrebbe detta nel 1981.
L'ha smentita 15 anni dopo? Mi sa che e' un po' tardino... gatta ci cova.
La frase è di un ingegnere IBM. :)
Comunque che ne poteva il povero Gates allora?
Ha ereditato la architettura Intel 8086, e se l'e' tenuta cosi' come'era.
Avrebbe anche potuto pestare i piedi e piangere ma, allora, dubito che alla Intel l'avrebbero ascoltato. Oggi forse invece...
Non poteva farci niente: il progetto 8086 era già nato diversi anni prima, e quando IBM strinse l'accordo con MS per la realizzazione del s.o. per il suo PC, l'architettura di quest'ultimo era già ben definita. ;)
Ma voi ricordate le frasi dette 15 anni fa? :stordita:
cdimauro
27-03-2008, 21:45
Mica tutte. Su questa s'è costruita una leggenda metropolitana che ancora oggi spopola.
Peccato che non ricordi il (cog)nome dell'ingegnere (mi pare iniziasse con la E).
DioBrando
28-03-2008, 01:15
Non lo sapevo dell'errata attribuzione, ho cercato un po' in giro e sembra tu abbia ragione.
Bill Gates l'ha smentita nel 1996 durante un'intervista.
PEccato pero' che la frase l'avrebbe detta nel 1981.
L'ha smentita 15 anni dopo? Mi sa che e' un po' tardino... gatta ci cova.
Se tra le fonti che hai guardato in rete ti è capitata quella di Wikipedia puoi leggere come in realtà l'avesse smentita già prima.
In ogni caso permettimi ma il fatto che appaia su di una intervista nel 96 non significa che prima non l'abbia mai smentita.
Non tutte le dichiarazioni vengono riportate, catalogate e soprattutto per intero.
Probabilmente alla ennesima volta in cui gli hanno stracciato i maroni ha voluto una volta per tutte precisarla.
In ogni caso qui (http://groups.google.com/group/alt.folklore.computers/msg/99ce4b0555bf35f4) si può leggere un estratto, da cui cito:
When IBM introduced its PC in 1981, many people attacked Microsoft for its
role. These critics said that 8-bit computers, which had 64K of address space,
would last forever. They said we were wastefully throwing out great 8-bit
programming by moving the world toward 16-bit computers.
We at Microsoft disagreed. We knew that even 16-bit computers, which had 640K
of available address space, would be adequate for only four or five years.
DioBrando
28-03-2008, 01:19
Ma voi ricordate le frasi dette 15 anni fa? :stordita:
No, ma se ti tartassano per una frase quando sei riuscito a fare ben altro, probabilmente farebbero ricordare a chiunque se l'abbia mai pronunciata o meno.
A proposito di IBM (http://bits.blogs.nytimes.com/2008/03/25/did-bill-gates-really-say-that/), cito:
The quote, “640K ought to be enough for anybody”; I first heard this in the early nineties and it was attributed to IBM (or someone there). This made sense since IBM came out with a personal computer with 640K memory. I have never heard it attributed to Bill Gates.
— Posted by Ravi Shankar
Se tra le fonti che hai guardato in rete ti è capitata quella di Wikipedia puoi leggere come in realtà l'avesse smentita già prima.
In ogni caso permettimi ma il fatto che appaia su di una intervista nel 96 non significa che prima non l'abbia mai smentita.
Non tutte le dichiarazioni vengono riportate, catalogate e soprattutto per intero.
Probabilmente alla ennesima volta in cui gli hanno stracciato i maroni ha voluto una volta per tutte precisarla.
In ogni caso qui (http://groups.google.com/group/alt.folklore.computers/msg/99ce4b0555bf35f4) si può leggere un estratto, da cui cito:
When IBM introduced its PC in 1981, many people attacked Microsoft for its
role. These critics said that 8-bit computers, which had 64K of address space,
would last forever. They said we were wastefully throwing out great 8-bit
programming by moving the world toward 16-bit computers.
We at Microsoft disagreed. We knew that even 16-bit computers, which had 640K
of available address space, would be adequate for only four or five years.
Sapevano già da allora che avrebbero creato Windows... :asd:
Probabilmente alla ennesima volta in cui gli hanno stracciato i maroni ha voluto una volta per tutte precisarla.
Mi sa che e' proprio cosi'.
Comunque chiunque ne capisce qualcosa di architetture e Sistemi Operativi capisce che quella frase lascia il tempo che trova.
Come ho detto prima, qualunque cosa avesse o non avesse detto Bill Gates al tempo e' ininfluente.
Avrebbe potuto pensare che 640k andavano bene, come anche che andassero bene 64k o non bastassero 4GB.
Tanto la decisione su quanta RAM poter montare e quindi indirizzare con il suo DOS non stava a lui ma alla Intel e alla IBM.
La quale non ha limitato l'indirizzamento a 1MB perche' gli piaceva cosi'.
Semplicemente se oggi portare 1 segnale e poi anche un pin in piu' di Address Bus costa qualcosa, allora costava molto ma molto di piu'.
Non per niente il databus dell 8086 era addirittura in comune con l'address bus (con somma gioia dei memory controller)
cdimauro
28-03-2008, 08:53
Mi sa che e' proprio cosi'.
Comunque chiunque ne capisce qualcosa di architetture e Sistemi Operativi capisce che quella frase lascia il tempo che trova.
Come ho detto prima, qualunque cosa avesse o non avesse detto Bill Gates al tempo e' ininfluente.
Avrebbe potuto pensare che 640k andavano bene, come anche che andassero bene 64k o non bastassero 4GB.
Tanto la decisione su quanta RAM poter montare e quindi indirizzare con il suo DOS non stava a lui ma alla Intel e alla IBM.
In primis a Intel, che ha messo il limite di 1MB per il processore. La frittata l'ha completata IBM, organizzando la memory map in maniera decisamente stupida, arrivando a occupare la memoria alt dal segmento B0000 in poi; non contenta della cazzata, con la scheda grafica EGA ha pensato bene di scendere fino al segmento A0000.
La quale non ha limitato l'indirizzamento a 1MB perche' gli piaceva cosi'.
Semplicemente se oggi portare 1 segnale e poi anche un pin in piu' di Address Bus costa qualcosa, allora costava molto ma molto di piu'.
Non per niente il databus dell 8086 era addirittura in comune con l'address bus (con somma gioia dei memory controller)
Esattamente, ma quella gestione astrusa dei segmenti se la poteva anche risparmiare: è una cazzata immane.
Internamente poteva benissimo usare i registri di segmento come facevano tante altre architetture a 16 bit dell'epoca: come BANCHI di memoria e non come aree sovrapponibili. Quindi indirizzando "linearmente" la memoria (potenzialmente fino a 4GB internamente).
Tra l'altro non avrebbe avuto neppure la necessità di aggiungere un sommatore in ogni parte del chip in cui doveva esserci la logica di generazione dell'indirizzo della memoria fisica, risparmiando ulteriori transistor.
Esternamente poi poteva tranquillamente continuare limitare il numero di bit di indirizzamento a 20, e continuare a indirizzare soltanto 1MB di memoria, come facevano già altre architetture (esempio la Motorola, che col 68000 "troncava" gli indirizzi a 24 bit e col 68008 a 20 bit, e col 68010 a 30 bit, ma internamente rimanevano sempre a 32 bit). ;)
Alla Intel gli ingegneri dovevano essere masochisti autolesionisti, visto che hanno continuato a fare cazzate anche con gli altri processori (vedi 286, a che indirizzava virtualmente 24 bit: gran passaggio quello da 20 a 24 bit, non c'è che dire).
...
Quoto tutto. L'ho sempre pensato anche io.
Anche se forse adesso avremmo ancora i 16bit e neppure i 32, altro che i 64.
E magari saremmo tutti piu' contenti e piu' veloci. Ma forse no. Boh.
cdimauro
28-03-2008, 09:04
Il passaggio ai 32 bit sarebbe arrivato ugualmente, e probabilmente negli stessi tempi: è il codice che spinge verso certe soluzioni architetturali, man mano che le esigenze cambiano (e si "complicano" le cose da fare). :)
Per il resto, sarei stato MOLTO più felice sicuramente da un'architettura "più lineare", e penso che anche la velocità ne avrebbe giovato (un'architettura meno complicata è più facile da "spingere" in termini di velocità di esecuzione).
3) Effects Model
§ Purely Functional is the right default
§ Imperative constructs are vital features
that must be exposed through explicit
effects-typing constructs:
questo invece è il punto che mi intriga di più e che si ricollega a quel che ha scritto mindwings.
Quelle sopra non sono affermazioni di poco conto.
La prima dice ad esempio che non si deve adeguare solo il programmatore, ma anche il framework che usa (e, in conclusione, la libreria standard del linguaggio), perche' altrimenti farlo diventa una perdita di tempo che non porta vantaggi. E' se non altro fattibile, in generale, senza portare tanti cambiamenti al linguaggio. Un buon esempio e' il lisp, che viene geralmente considerato funzionale, ma in realta' e' multiparadigma (il goto esiste anche in lisp :stordita: ), solo che ha come "right default" l'approccio funzionale. In generale ci cascano dentro un po' tutti i linguaggi funzionali, compresi quelli non puri, visto che, quando non si tratta di side-effects, tendono verso questo approccio.
La seconda e' ben ancora peggiore, in quanto dice ci deve essere una distinzione netta tra funzioni(/metodi) con side effects e quelle che non ce l'hanno, che una funzione che prende una stringa e la converte in numero e' sostanzialmente diversa da una che quel numero te lo ritorna da un file, perche' quest'ultima interagisce con il mondo esterno e non puoi usarla quando vuoi in vece della prima.
Questa distinzione la fanno pochissimi linguaggi mainstream (Haskell e mi sembra Clean) e, oltre a cambiare radicalmente il modo in cui ci programma, e' difficile da aggiungere in modo ragionevole ad un linguaggio senza cambiarlo profondamente
cdimauro
29-03-2008, 09:17
Ma poi un linguaggio puramente funzionale è ben difficile da programmare: ti costringe a tanti "contorsionismi" che con linguaggi già non puramente funzionali (è sufficiente l'operazione di assegnazione per rendere la vita più facile :p) si risolvono senza troppi sbattimenti di testa. ;)
Ma poi un linguaggio puramente funzionale è ben difficile da programmare: ti costringe a tanti "contorsionismi" che con linguaggi già non puramente funzionali (è sufficiente l'operazione di assegnazione per rendere la vita più facile :p) si risolvono senza troppi sbattimenti di testa. ;)
Non e' difficile, e' diverso.
Alcune cose sono piu' complesse, altre piu' semplici.
In un linguaggio puramente funzionale alcune cose come iteratori, revisioning (tenere vecchie versioni di un oggetto) vengono praticamente gratis. La memoria viene allocata e condivisa tra oggetti diversi automaticamente. Altre cose sono proprio impossibili da ottenere o richiedono algoritmi differenti (le code ad esempio)
Ovvio che per chi e' abituato in modo diverso sono contorsionismi.
In ogni caso trovo che una volta presa mano i vantaggi siano notevoli, soprattutto quando ci si rende conto di quanto sforzo mentali porti via il dover considerare i side effects.
Attenzione comunque che sopra non si parlava di linguaggi puramente funzionali, ma di preferire la programmare in modo puramente funzionale quando possibile.
Quel che volevo dire quanto questo sia possibile dipende molto dal supporto che viene dal linguaggio e dalla sua libreria.
In python ad esempio possiamo considerare la list comprehension come qualcosa di puramente funzionale, ma d'altra parte il metodo sort delle liste non lo e', per cui uno dovrebbe farsi sempre una copia della lista prima di ordinarla.
cdimauro
29-03-2008, 21:25
Esattamente, ma spesso si opera in locale, cioé non è necessario mantenere anche la vecchia lista.
Per un approccio puramente funzionale basta usare la funzione built-in sorted(). :)
Comunque all'università non mi sono trovato male con la programmazione funzionale, e il mio prof. di linguaggi di programmazione (il mitico Giovanni Gallo :)) s'è prodigato molto per farci apprezzare le meraviglie di questo paradigma con Scheme.
Debbo dire che ho apprezzato e mi affascina molto, tanto che spesso tendo a esagerare (e Fran per questo mi prende a mazzate un giorno sì, e l'altro pure :asd:).
Soprattutto mi affascina il fatto che con la programmazione funzionale pura è più facile testare la correttezza del codice.
tomminno
07-04-2008, 09:50
Per ritornare in topic ho trovato goto anche nel codice per creazione dei processi e in quasi tutti i metodi dei Socket.
Ah e chi sostiene che con la programmazione ad oggetti eviti gli if?
Vedo sempre controlli del tipo
if (nonRispettaIRequisiti)
throw EccezioneDiQualcheTipo()
E non potrebbe essere altrimenti.
cdimauro
07-04-2008, 13:28
Ne avevemo già parlato del perché serva almeno un if: http://www.hwupgrade.it/forum/showpost.php?p=21537814&postcount=48 ;)
tomminno
07-04-2008, 13:38
Ne avevemo già parlato del perché serva almeno un if: http://www.hwupgrade.it/forum/showpost.php?p=21537814&postcount=48 ;)
Lo so benissimo, solo che ho letto tante volte discorsi del tipo "con la programmazione OOP eviti gli if", oppure "io non uso gli if ma mi affido alle eccezioni".
E quotando il tuo post:
La prassi con C & affini è quella della catena di if, dal primo che l'ha rilevata fino all'ultimo che la deve poi gestire. Tutti if condizionali, che, come sai, sono i peggiori da trattare per un processore.
Anche la prassi del C# è quella di una catena di if per vedere quale possibile eccezione sollevare.
cdimauro
07-04-2008, 13:47
Non è certo la stessa cosa che ripetere gli n controlli necessari per tutti i "livelli"...
Comunque quelli che riporti sono ovviamente slogan: la programmazione OOP non può eliminare gli if, ma certamente contribuisce, se ben usata, a ridurli anche di molto. ;)
Anche la prassi del C# è quella di una catena di if per vedere quale possibile eccezione sollevare.
Assolutamente no. Dipende dal design del codice.
tomminno
07-04-2008, 13:52
Assolutamente no. Dipende dal design del codice.
E questo design come lo definiresti?
if (this.disposed)
{
throw new ObjectDisposedException(base.GetType().Name);
}
if (!string.IsNullOrEmpty(startInfo.UserName) || (startInfo.Password != null))
{
throw new InvalidOperationException(SR.GetString("CantStartAsUser"));
}
if ((startInfo.RedirectStandardInput || startInfo.RedirectStandardOutput) || startInfo.RedirectStandardError)
{
throw new InvalidOperationException(SR.GetString("CantRedirectStreams"));
}
if (startInfo.StandardErrorEncoding != null)
{
throw new InvalidOperationException(SR.GetString("StandardErrorEncodingNotAllowed"));
}
if (startInfo.StandardOutputEncoding != null)
{
throw new InvalidOperationException(SR.GetString("StandardOutputEncodingNotAllowed"));
}
if (startInfo.environmentVariables != null)
{
throw new InvalidOperationException(SR.GetString("CantUseEnvVars"));
}
Per non parlare poi di questo
ShellExecuteHelper helper = new ShellExecuteHelper(executeInfo);
if (helper.ShellExecuteOnSTAThread())
{
goto Label_0304;
}
int errorCode = helper.ErrorCode;
if (errorCode != 0)
{
goto Label_0282;
}
long hInstApp = (long) executeInfo.hInstApp;
if (hInstApp <= 8L)
{
if (hInstApp < 2L)
{
goto Label_0276;
}
switch (((int) (hInstApp - 2L)))
{
case 0:
errorCode = 2;
goto Label_0282;
case 1:
errorCode = 3;
goto Label_0282;
case 2:
case 4:
case 5:
goto Label_0276;
case 3:
errorCode = 5;
goto Label_0282;
case 6:
errorCode = 8;
goto Label_0282;
}
}
if ((hInstApp <= 0x20L) && (hInstApp >= 0x1aL))
{
switch (((int) (hInstApp - 0x1aL)))
{
case 0:
errorCode = 0x20;
goto Label_0282;
case 1:
goto Label_0276;
case 2:
case 3:
case 4:
errorCode = 0x484;
goto Label_0282;
case 5:
errorCode = 0x483;
goto Label_0282;
case 6:
errorCode = 0x485;
goto Label_0282;
}
}
Label_0276:
errorCode = (int) executeInfo.hInstApp;
Label_0282:
throw new Win32Exception(errorCode);
E questo design come lo definiresti?
if (this.disposed)
{
throw new ObjectDisposedException(base.GetType().Name);
}
if (!string.IsNullOrEmpty(startInfo.UserName) || (startInfo.Password != null))
{
throw new InvalidOperationException(SR.GetString("CantStartAsUser"));
}
if ((startInfo.RedirectStandardInput || startInfo.RedirectStandardOutput) || startInfo.RedirectStandardError)
{
throw new InvalidOperationException(SR.GetString("CantRedirectStreams"));
}
if (startInfo.StandardErrorEncoding != null)
{
throw new InvalidOperationException(SR.GetString("StandardErrorEncodingNotAllowed"));
}
if (startInfo.StandardOutputEncoding != null)
{
throw new InvalidOperationException(SR.GetString("StandardOutputEncodingNotAllowed"));
}
if (startInfo.environmentVariables != null)
{
throw new InvalidOperationException(SR.GetString("CantUseEnvVars"));
}
Cosi':
http://www.dailyblogtips.com/wp-content/uploads/codinghorror.gif
tomminno
07-04-2008, 14:07
Cosi':
http://www.dailyblogtips.com/wp-content/uploads/codinghorror.gif
Immaginavo :D
Peccato che quello è il modo in cui il .NET solleva le eccezioni.
E sinceramente non so come altro potrebbe fare.
Immaginavo :D
Peccato che quello è il modo in cui il .NET solleva le eccezioni.
E sinceramente non so come altro potrebbe fare.
NullObject pattern e passa la paura. Il problema di quel codice non e' l'uso dei goto, ma chi lo ha scritto.
Se mi passa sotto gli occhi una catena di if cosi' ad una review, io non faccio fare il commit. E puo' piangere in tutte le lingue che vuole.
tomminno
07-04-2008, 14:54
NullObject pattern e passa la paura. Il problema di quel codice non e' l'uso dei goto, ma chi lo ha scritto.
Se mi passa sotto gli occhi una catena di if cosi' ad una review, io non faccio fare il commit. E puo' piangere in tutte le lingue che vuole.
Evidentemente chi sovrintende alla scrittura del .NET non è pignolo come te ;)
Però scusa il null object pattern non solleva eccezioni, semplicemente crea un oggetto che non fa niente, ma come farebbe il framework a sollevarti una eccezione?
E' chiaro che deve controllare se un oggetto è nullo, se il valore è fuori range ecc...
E questo lo può fare solo con una catena di if che controlli che ogni parametro passato non sia nullo, ecc...
Evidentemente chi sovrintende alla scrittura del .NET non è pignolo come te ;)
Dipende dal team di sviluppo. Molti team di sviluppo in MS hanno degli ingegneri che si occupano solo del testing ed hanno potere di vita o di morte sul codice: se non rispetta gli standard qualitativi si riscrive. Purtroppo non tutti i team lavorano cosi'.
Però scusa il null object pattern non solleva eccezioni, semplicemente crea un oggetto che non fa niente, ma come farebbe il framework a sollevarti una eccezione?
Easy.
Redirector redirector = object.GetRedirector();
redirector.WriteSomething("bla bla bla");
class NullRedirector: public Redirector
{
...
void WriteSomething(String string)
{
throw NOOOOWAYException("WriteSomething called on a NullRedirector, you twat");
}
}
Inizializzi object nel costruttore per usare un NullRedirector di default e se nessuno sovrascrive quella proprieta' ti viene sparata un'eccezione al momento dell'uso. Nessun if di mezzo.
Good design is simple and communicate intensions well and clearly.
Wow davvero utile questo pattern! :eek:
Un solo dubbio: quando l'user della libreria chiama WriteSomething potrebbe essere troppo tardi, il codice precedente avrebbe potuto sbagliare qualcosa considerando NullRedirector come un Redirector vero... a meno che ogni singolo metodo di NullRedirector non lanci un'eccezione :confused:
Eppoi, non serve comunque una caterva di if per decidere se creare o no il NullObject?
Ma d'altra parte non c'è modo di evitare a qualcuno di farsi male con le sue mani :D
PS: Articolo contro l'uso delle eccezioni (http://www.codercorner.com/blog/?p=33)
Non so quanto possa essere vero... ma sembra convincente.
Wow davvero utile questo pattern! :eek:
Dipende! Non iniziare a creare NullObject ovunque adesso :D
Un solo dubbio: quando l'user della libreria chiama WriteSomething potrebbe essere troppo tardi, il codice precedente avrebbe potuto sbagliare qualcosa considerando NullRedirector come un Redirector vero... a meno che ogni singolo metodo di NullRedirector non lanci un'eccezione :confused:
NullObject e' definito come un oggetto che gestisce tutte le situazioni nelle quali l'oggetto e' nullo. Quindi l'implementazione di ogni metodo dipende dallo scenario. Magari un'implementazione piu' appropriata di WriteSomething poteva essere non fare assolutamente nulla.
Scegli di caso in caso.
Eppoi, non serve comunque una caterva di if per decidere se creare o no il NullObject?
Dipende dal tuo scenario, in genere direi di no: puoi ad esempio inizializzare la proprieta' 'redirector' di un oggetto ad un'istanza di NullObject nel costruttore:
MyObject::MyObject()
: redirector(new NullRedirector)
{
// whatever
}
void SetRedirector(Redirector new_redirector)
{
redirector = new_redirector;
}
Se nessuno invoca SetRedirector e provi a usare la proprieta' redirector di MyObject, verra' invocato il comportamento di NullRedirector, che puo' essere il fare nulla o lanciare un'eccezione.
tomminno
07-04-2008, 16:33
Dipende dal team di sviluppo. Molti team di sviluppo in MS hanno degli ingegneri che si occupano solo del testing ed hanno potere di vita o di morte sul codice: se non rispetta gli standard qualitativi si riscrive. Purtroppo non tutti i team lavorano cosi'.
Direi che quello che si occupa del .NET dovrebbe essere uno dei team principali, vista la profusione di risorse rivolte esclusivamente al .NET.
Il futuro di Microsoft è il .NET.
Easy.
Redirector redirector = object.GetRedirector();
redirector.WriteSomething("bla bla bla");
class NullRedirector: public Redirector
{
...
void WriteSomething(String string)
{
throw NOOOOWAYException("WriteSomething called on a NullRedirector, you twat");
}
}
Inizializzi object nel costruttore per usare un NullRedirector di default e se nessuno sovrascrive quella proprieta' ti viene sparata un'eccezione al momento dell'uso. Nessun if di mezzo.
Good design is simple and communicate intensions well and clearly.
Però così agisci solo a livello di costruzione dell'oggetto e la validazione dei dati?
Che succede se scrivi:
redirector.WriteSomething(null);
evidentemente a livello di framework il metodo WriteSomething sarà scritto nella forma:
string WriteSomething(string something)
{
if (something == null)
throw ArgumentNullException("something is null");
...
}
E se, come nel caso della creazione di un processo, hai specificato in ProcessStartInfo dei parametri non compatibili tra loro? Ad esempio UseShellExecute e il RedirectStandardInput o RedirectStandardOutput?
E' chiaro che ti ci vuole il famigerato if.
Sinceramente di alternative non ne vedo e se hanno riempito il .NET di tutti questi if evidentemente altre strade non c'erano (o se c'erano non erano percorribili).
evidentemente a livello di framework il metodo WriteSomething sarà scritto nella forma:
string WriteSomething(string something)
{
if (something == null)
throw ArgumentNullException("something is null");
...
}
Ma anche no. Come provi ad usare una stringa null, il runtime spara gia' un eccezione, non devi farlo tu. Questo controllo e' una duplicazione perfettamente inutile e puo' essere tolto :)
E se, come nel caso della creazione di un processo, hai specificato in ProcessStartInfo dei parametri non compatibili tra loro? Ad esempio UseShellExecute e il RedirectStandardInput o RedirectStandardOutput?
E' chiaro che ti ci vuole il famigerato if.
Oppure ti ci vuole un bello State pattern o uno Strategy a seconda della situazione :)
In generale credo ci voglia una bella lettura del libro sui Design Pattern.
Chiaro, se programmi come fossi in C a colpi di flag non ti verra' mai in mente una soluzione alternativa e piu' semplice all'if, ma qui il problema e' a monte: l'aver imparato prima il C.
Sinceramente di alternative non ne vedo e se hanno riempito il .NET di tutti questi if evidentemente altre strade non c'erano (o se c'erano non erano percorribili).
C'e' sempre una strada per rendere il design piu' semplice e robusto.
Fek, mi citi la tua top-5 riguardo a dei libri?
tomminno
08-04-2008, 08:48
Ma anche no. Come provi ad usare una stringa null, il runtime spara gia' un eccezione, non devi farlo tu. Questo controllo e' una duplicazione perfettamente inutile e puo' essere tolto :)
Non è il runtime a sollevare le eccezioni, ma direttamente il codice delle classi .NET perchè esegue i controlli tramite if.
Gli spezzoni che ho postato sono tutti presi da mscorlib.dll
Tutte le volte che passi una classe ad un metodo del framework .NET c'è un if != null dietro ben prima del runtime.
Oppure ti ci vuole un bello State pattern o uno Strategy a seconda della situazione :)
In generale credo ci voglia una bella lettura del libro sui Design Pattern.
Chiaro, se programmi come fossi in C a colpi di flag non ti verra' mai in mente una soluzione alternativa e piu' semplice all'if, ma qui il problema e' a monte: l'aver imparato prima il C.
C'e' sempre una strada per rendere il design piu' semplice e robusto.
Evidentemente anche quelli che hanno scritto il .NET hanno imparato prima il C.
Comunque non ho ancora capito come controllare se un riferimento passato è nullo, sarà che ho cominciato con il C :fagiano:
C'e' sempre una strada per rendere il design piu' semplice e robusto.
Ma chi ha scritto il .NET non l'ha messa in pratica
Fek, mi citi la tua top-5 riguardo a dei libri?
Niente top-5 di Fek... :cry:
Non è il runtime a sollevare le eccezioni, ma direttamente il codice delle classi .NET perchè esegue i controlli tramite if.
Gli spezzoni che ho postato sono tutti presi da mscorlib.dll
Tutte le volte che passi una classe ad un metodo del framework .NET c'è un if != null dietro ben prima del runtime.
No, e' il runtime. Quegli if sono inutili, che siano scritti da te o da qualcun altro cambia poco.
Object obj = null;
obj.DoAnything();
Il CLR spara una NullException. Quindi non hai bisogno di un if prima.
Evidentemente anche quelli che hanno scritto il .NET hanno imparato prima il C.
Qualcuno sicuramente, non tutto il codice e' come quello che hai postato pero'. C'e' anche dell'ottimo codice. Se dai un'occhio a WCF il cui technical director e' Don Box, difficilmente ci trovi if a cascata come quelli.
Comunque non ho ancora capito come controllare se un riferimento passato è nullo, sarà che ho cominciato con il C :fagiano:
Ti ho fatto degli esempi :)
Il resto dipende, lo ripeto, dal design: non puoi sperare di prendere due righe di codice e chiedere come eliminare un if se non dai uno sguardo al contesto dell'architettura per poterla semplificare. Un NullObject pattern non e' la soluzione. A volte una soluzione potrebbe essere una hash map ad esempio.
Ma chi ha scritto il .NET non l'ha messa in pratica
Come ho detto, non tutto il codice di .NET per fortuna e' scritto in quella maniera.
Niente top-5 di Fek... :cry:
Test-Driven Development di Beck
Refactoring di Fowler
Refactoring To Patterns di Krievesky
Design Patterns della Gang Of Four
Code Complete di adesso non ricordo il nome.
Test-Driven Development di Beck
Refactoring di Fowler
Refactoring To Patterns di Krievesky
Design Patterns della Gang Of Four
Code Complete di adesso non ricordo il nome.
:eek:
tomminno
08-04-2008, 09:50
No, e' il runtime. Quegli if sono inutili, che siano scritti da te o da qualcun altro cambia poco.
Si ma le classi .NET fanno controlli prima di arrivare al runtime.
Object obj = null;
obj.DoAnything();
Il CLR spara una NullException. Quindi non hai bisogno di un if prima.
In questo caso è il runtime certamente, ma in questo caso non lo è:
char[]toWrite = null;
StreamWriter sw = new StreamWriter("file.txt");
sw.Write(toWrite,0,10);
in questo caso l'eccezione è sollevata dal metodo Write di StreamWriter che esegue come prima cosa il controllo
if (buffer == null)
{
throw new ArgumentNullException("buffer", Environment.GetResourceString("ArgumentNull_Buffer"));
}
e il costruttore di StreamWriter controlla se il path passato non è null:
public StreamWriter(Stream stream, Encoding encoding, int bufferSize) : base(null)
{
if ((stream == null) || (encoding == null))
{
throw new ArgumentNullException((stream == null) ? "stream" : "encoding");
}
if (!stream.CanWrite)
{
throw new ArgumentException(Environment.GetResourceString("Argument_StreamNotWritable"));
}
if (bufferSize <= 0)
{
throw new ArgumentOutOfRangeException("bufferSize", Environment.GetResourceString("ArgumentOutOfRange_NeedPosNum"));
}
this.Init(stream, encoding, bufferSize);
}
Ed è così per praticamente tutte le classi appartenenti al framework.
Lanci un thread?
public Thread(ThreadStart start)
{
if (start == null)
{
throw new ArgumentNullException("start");
}
this.SetStartHelper(start, 0);
}
Scrivi un socket server?
public Socket Accept()
{
if (Logging.On)
{
Logging.Enter(Logging.Sockets, this, "Accept", "");
}
if (this.CleanedUp)
{
throw new ObjectDisposedException(base.GetType().FullName);
}
if (this.m_RightEndPoint == null)
{
throw new InvalidOperationException(SR.GetString("net_sockets_mustbind"));
}
if (!this.isListening)
{
throw new InvalidOperationException(SR.GetString("net_sockets_mustlisten"));
}
if (this.m_IsDisconnected)
{
throw new InvalidOperationException(SR.GetString("net_sockets_disconnectedAccept"));
}
...
Ti ho fatto degli esempi :)
Si lo so ma senza un refactoring dell'interfaccia delle classi del .NET li vedo di difficile applicazione.
Il resto dipende, lo ripeto, dal design: non puoi sperare di prendere due righe di codice e chiedere come eliminare un if se non dai uno sguardo al contesto dell'architettura per poterla semplificare. Un NullObject pattern non e' la soluzione. A volte una soluzione potrebbe essere una hash map ad esempio.
Mi capita di usare nei protocolli di comunicazione le map con il NullObject, se il valore non è presente nella mappa finisce sull'oggetto che non fa niente.
Semplicissimo e retrocompatibile.
Come ho scritto, non tutto il codice di .NET per fortuna e' scritto in quella maniera.
Forse non tutto ma tutte le classi base o comunque quelle che si utilizzano più comunemente si.
Si ma le classi .NET fanno controlli prima di arrivare al runtime.
Ma sbagliano, perche' lo fa gia' il runtime. E' un'inutile duplicazione.
in questo caso l'eccezione è sollevata dal metodo Write di StreamWriter che esegue come prima cosa il controllo
if (buffer == null)
{
throw new ArgumentNullException("buffer", Environment.GetResourceString("ArgumentNull_Buffer"));
}
Non serve, perche' lo fa gia' il runtime al primo accesso al buffer. Un controllo di nullness e' un'inutile duplicazione.
e il costruttore di StreamWriter controlla se il path passato non è null:
Indovina? Non serve, perche' lo fa gia' il runtime al primo accesso al path. E' un'inutile duplicazione.
Ed è così per praticamente tutte le classi appartenenti al framework.
E non serve, perche' lo fa gia' il runtime, e' un'inutile duplicazione.
Si lo so ma senza un refactoring dell'interfaccia delle classi del .NET li vedo di difficile applicazione.
Non devi fare tu quel refactoring, ma chi di dovere che lavora sul framework di .NET, che non gode purtroppo di infallibilita' papale.
Forse non tutto ma tutte le classi base o comunque quelle che si utilizzano più comunemente si.
E sono anche quelle piu' vecchie...
Questa non e' certo una scusa per scrivere codice di bassa qualita' "perche' alcune classi di .NET sono scritte cosi'". La prima skill di un buon programmatore e' saper evolvere il proprio stile e migliolarlo con nuovi strumenti. Se ti fossilizzi ad usare if dove strumenti migliori ti porterebbero a codice piu' semplice e mantenibile, sbagli. Io guardo il codice che ho scritto l'anno scorso e lo trovo scritto male e migliorabile, mi aspetto che chi ha lavorato sul framework di .NET pensi la stessa cosa di classi che ha scritto anni fa.
Il codice nuovo nel framework e' di qualita' decisamente fortunatamente.
secondo me .NET è implementato in quel modo per motivi prestazionali. senza dubbio le soluzioni proposte da fek sono più leggibili ed eleganti, ma probabilmente sollevare un'eccezione ogni 3 righe di codice ha un'impatto importante sulle prestazioni. dico probabilmente perchè non l'ho scritto io il codice ( per fortuna :P )
Test-Driven Development di Beck
Refactoring di Fowler
Refactoring To Patterns di Krievesky
Design Patterns della Gang Of Four
Code Complete di adesso non ricordo il nome.
Concordo e rilancio.
Non e' un libro, ma solo un'insieme di regole.
anche se vecchie e pensate solo per il mondo UNIX io continuo a considerarle attuali.
http://www.faqs.org/docs/artu/ch01s06.html
secondo me .NET è implementato in quel modo per motivi prestazionali. senza dubbio le soluzioni proposte da fek sono più leggibili ed eleganti, ma probabilmente sollevare un'eccezione ogni 3 righe di codice ha un'impatto importante sulle prestazioni. dico probabilmente perchè non l'ho scritto io il codice ( per fortuna :P )
Beh, una catena di if su quasi qualunque processore moderno non e' esattamente una grandissima idea dal punto di vista prestazionale. Inoltre, da sempre, il codice piu' veloce e' quello che non scrivi (ed e' anche l'unico codice senza bug e che non va mantenuto): mettere un if dove e' perfettamente inutile certamente non velocizza il framework.
Quel codice e' scritto cosi' semplicemente perche e' stato scritto male.
Test-Driven Development di Beck
Refactoring di Fowler
Refactoring To Patterns di Krievesky
Design Patterns della Gang Of Four
Code Complete di adesso non ricordo il nome.
Essendo il primo un po' vecchiotto ho cercato e ho trovato questo:
http://www.amazon.com/Test-Driven-Acceptance-Java-Developers/dp/1932394850
Ne parlano bene, qualcuno l'ha letto?
E poi, sai consigliarmi un buon libro che tratti di sicurezza informatica?
Grazie, scusate il piccolo ot
l'if null, potrebbe essere utile se fatto prima di un lavoro oneroso(in cui nn si usa ancora il parametro passato), o se il catch dell'eccezione del runtime fosse particolarmente oneroso(ma nn mi sembra proprio il caso)
cmq in quelle classi il catch dell'eccezioni mi sembra fatto unicamente per comunicare che nn è avvenuta una normale NPE, ma che è stato passato un argomento a null, per rendere l'errore più parlane.
Un po come la più generica illegaleArgumentException in java
allora non c'è proprio niente da fare per .NET :sofico:
@gugoXX
anch'io rileggendole poco tempo fa le ho trovate tremendamente attuali
Test-Driven Development di Beck
Refactoring di Fowler
Refactoring To Patterns di Krievesky
Design Patterns della Gang Of Four
Code Complete di adesso non ricordo il nome.
Tombola! :stordita:
Code Complete è di McConnell, Microsoft Press.
DioBrando
09-04-2008, 08:46
Essendo il primo un po' vecchiotto ho cercato e ho trovato questo:
http://www.amazon.com/Test-Driven-Acceptance-Java-Developers/dp/1932394850
Ne parlano bene, qualcuno l'ha letto?
Sì, l'ho consigliato qui (http://www.hwupgrade.it/forum/showthread.php?t=1703331&highlight=TDD).
E' stato linkato altro materiale sul tema :)
E poi, sai consigliarmi un buon libro che tratti di sicurezza informatica?
Grazie, scusate il piccolo ot
Sicurezza informatica in generale o metodologie mirate ad uno sviluppo di applicazioni "sicure"?
Sicurezza informatica in generale o metodologie mirate ad uno sviluppo di applicazioni "sicure"?
Tutti e due, un po' di teoria e un po' di pratica (senza dettagli sugli algoritmi
di crittografia)
E che siano possibilmente sintetici, sembra che gli editori paghino a numero di pagine...
Grazie
DioBrando
09-04-2008, 12:25
Tutti e due, un po' di teoria e un po' di pratica (senza dettagli sugli algoritmi
di crittografia)
E che siano possibilmente sintetici, sembra che gli editori paghino a numero di pagine...
Grazie
Sintesi quando si parla di sicurezza è un po' dura :)
Cmq...dando per scontato che tu conosca gli aspetti legati alla crittografia e alle reti in generale (di solito prendo come riferimento il testo di Tanenbaum), non posso non consigliarti il libro di Zalewski: "Il rumore dell'hacking".
E' piuttosto tecnico seppur scorrevole e tratta tematiche spesso tralasciate nei libri general generici; lo trovi su Amazon con il titolo originale "Silence on the Wire" ad un prezzo molto modico.
Per quanto riguarda le metodologie di sviluppo sono fuori e non nessun libro segnato ma ti lascio lo stesso due risorse che penso possano riverlarsi utili:
ISECOM (http://www.isecom.org/): è un istituto che si occupa di sicurezza ed in particolare di tutte le metodologie cosiddette Open/white hacking.
Trovi informazioni in generale e anche sulle certificazioni casomai ti interessasse approfondire fino a quel livello.
Sempre sull'argomento sviluppatore: 4 articoli (http://www.programmazione.it/index.php?entity=eitem&idItem=35317).
Non è un granchè ma ora sono senza "bibliografia" :D
khelidan1980
09-04-2008, 12:28
Sintesi quando si parla di sicurezza è un po' dura :)
Cmq...dando per scontato che tu conosca gli aspetti legati alla crittografia e alle reti in generale (di solito prendo come riferimento il testo di Tanenbaum), non posso non consigliarti il libro di Zalewski: "Il rumore dell'hacking".
E' piuttosto tecnico seppur scorrevole e tratta tematiche spesso tralasciate nei libri general generici; lo trovi su Amazon con il titolo originale "Silence on the Wire" ad un prezzo molto modico.
Per quanto riguarda le metodologie di sviluppo sono fuori e non nessun libro segnato ma ti lascio lo stesso due risorse che penso possano riverlarsi utili:
ISECOM (http://www.isecom.org/): è un istituto che si occupa di sicurezza ed in particolare di tutte le metodologie cosiddette Open/white hacking.
Trovi informazioni in generale e anche sulle certificazioni casomai ti interessasse approfondire fino a quel livello.
Sempre sull'argomento sviluppatore: 4 articoli (http://www.programmazione.it/index.php?entity=eitem&idItem=35317).
Non è un granchè ma ora sono senza "bibliografia" :D
Ma tu sei una biblioteca ambulante :D :D
DioBrando
09-04-2008, 12:41
Ma tu sei una biblioteca ambulante :D :D
lol
Adoro leggere :stordita:
E la sicurezza è uno degli argomenti che mi è sempre piaciuto di più :)
In ogni caso in rete c'è veramente tanto materiale sul tema, dai tutorial su come rompere le protezioni, testare le proprie applicazioni...
Avevo trovato anche dei server con prove tipo quelle che vengono eseguite per il Capture The Flag.
Tombola! :stordita:
Code Complete è di McConnell, Microsoft Press.
Vicius ma Code Complete 2 è il seguito di Code Complete seconda edizione oppure è proprio un libro che va a sostituire il primo? :what:
X DioBrando: A me interessa qualcosa che non tratti la sicurezza in generale bensi a livello di codice (C, C++, Java).
C'è qualcosa? Ho l'impressione che molte volte quando si parli di sicurezza ci sono un sacco di libri che come target hanno il bimbo in preda ad una crisi di identità, a me servirebbe qualcosa di tecnico assai, che illustri i buffer overflow, per esempio, e tutte quelle pratiche "in codice" che in genere causano problemi di sicurezza e siano causa di exploit. C'è qualcosa che tu sappia?
EDIT: Se poi come target ha Unix, ancora meglio :)
Provengo dalla scuola di Richard Stevens, non so se mi intendi, che secondo me ha scritto i migliori libri della storia ;)
Il mio sogno invece sarebbe un'edizione moderna e rivisitata del famosissimo libro di Charles Petzold che non sia orientato a C# :cry:
Vicius ma Code Complete 2 è il seguito di Code Complete seconda edizione oppure è proprio un libro che va a sostituire il primo? :what:
http://www.codinghorror.com/blog/archives/000022.html
lol
Adoro leggere :stordita:
E la sicurezza è uno degli argomenti che mi è sempre piaciuto di più :)
In ogni caso in rete c'è veramente tanto materiale sul tema, dai tutorial su come rompere le protezioni, testare le proprie applicazioni...
Avevo trovato anche dei server con prove tipo quelle che vengono eseguite per il Capture The Flag.
Mi suicidio di fronte a tanta competenze, ti prego non mi bloccare sto piangendo :cry:
http://www.codinghorror.com/blog/archives/000022.html
Appunto, a me sembra che Code Complete 2 in realtà sia una riscrittura del primo e non vada inteso come un "secondo volume"... :stordita:
Il titolo però lascia presagire diversamente. E' abbastanza fuorviante...
EDIT: non ci si crede, amazon.com è offline! :eek:
Vicius ma Code Complete 2 è il seguito di Code Complete seconda edizione oppure è proprio un libro che va a sostituire il primo? :what:
X DioBrando: A me interessa qualcosa che non tratti la sicurezza in generale bensi a livello di codice (C, C++, Java).
C'è qualcosa? Ho l'impressione che molte volte quando si parli di sicurezza ci sono un sacco di libri che come target hanno il bimbo in preda ad una crisi di identità, a me servirebbe qualcosa di tecnico assai, che illustri i buffer overflow, per esempio, e tutte quelle pratiche "in codice" che in genere causano problemi di sicurezza e siano causa di exploit. C'è qualcosa che tu sappia?
Roba tipo questo?
http://www.amazon.com/Writing-Secure-Second-Michael-Howard/dp/0735617228/ref=pd_bbs_sr_1?ie=UTF8&s=books&qid=1207743543&sr=8-1
Se navighi un pò tra i link di amazon ne trovi quanti ne vuoi di libri sul tema.
Roba tipo questo?
http://www.amazon.com/Writing-Secure-Second-Michael-Howard/dp/0735617228/ref=pd_bbs_sr_1?ie=UTF8&s=books&qid=1207743543&sr=8-1
Se navighi un pò tra i link di amazon ne trovi quanti ne vuoi di libri sul tema.
Amazon.com lo "navigo" regolarmente. A me non interessa trovare libri sul tema, mi interessa trovarne di buoni. Generalmente faccio affidamento alle recensioni degli utenti per rendermi conto di come quel libro è. Solo che molte volte pure i libri sono "overrated" o soggetti a hype :stordita:
Ma a te amazon.com risulta online? :eek:
Io attualmente sto leggendo questo:
http://ecx.images-amazon.com/images/I/512lFy8BxCL._SL500_BO2,204,203,200_PIsitb-dp-500-arrow,TopRight,45,-64_OU02_AA240_SH20_.jpg
:stordita:
m.distrutti
09-04-2008, 15:54
(di solito prendo come riferimento il testo di Tanenbaum
lo sogno di notte Tanenbaum *.*
(:Prrr: )
cmq da amazon.com i libri che voglio comprare io li fanno pagare troppo >.> e il più delle volte per le spedizioni intercontinentali bisogna mettersi daccordo con il venditore che chiede una cifra spropositata T.T
amazon.uk e' gia meglio anche se noto che la community di amazon.com ha più libri :D
Oggi e' stato un momento emozionante, uno di quei giorni nei quali pensi che ci sia speranza per un mondo migliore, un mondo senza sovraingegnerizzazioni, un mondo senza ore perse di fronte al nulla, un mondo senza Python (ok, questa era gratuita :asd: ).
Oggi un mio collega nuovo durante una discussione di design mi ha detto: "You don't like simple code, do you?"
Ma ma ma... Gli ho risposto "When I write code, I'm driven by YAGNI".
Lui di rimando "It means I'm more draconian than you".
Per i non anglofili, mi ha detto che lui segue YAGNI piu' fedelmente di me. Credo di essere innamorato, e' anche un bel ragazzo :D
Per i non anglofili, mi ha detto che lui segue YAGNI piu' fedelmente di me. Credo di essere innamorato, e' anche un bel ragazzo :D
:asd: l'abbiamo perso :doh:
Per i non anglofili, mi ha detto che lui segue YAGNI piu' fedelmente di me. Credo di essere innamorato, e' anche un bel ragazzo :D
Ma lascia perdere... come stanno le tue amiche slovacche invece?
Mi suicidio di fronte a tanta competenze, ti prego non mi bloccare sto piangendo :cry: lol? perché prendi in giro DioBrando imitando MasterDany? :asd:
m.distrutti
09-04-2008, 17:22
lol? perché prendi in giro DioBrando imitando MasterDany? :asd:
verba volant, scripta etiam si facias aeroplaninum
penis abundat in ore puttanarum
hauhauahauhauh l'ho letta solo ora T.T
mandami una tua foto cosi sogno anche te oltre tanenbaum rotfl:D :mc: :mc:
Vicius ma Code Complete 2 è il seguito di Code Complete seconda edizione oppure è proprio un libro che va a sostituire il primo? :what:
Sostituisce proprio il primo. Se lo vuoi prendere evita di l'edizione italiana che costa sugli 80€ :mad:
DioBrando
09-04-2008, 19:08
Mi suicidio di fronte a tanta competenze, ti prego non mi bloccare sto piangendo :cry:
ahahahaahfjkshfaksjggkh :sbonk:
manca poco mi vada di traverso il panino :asd:
OT: sn tornato ora e mi sto rivedendo Liverpool-Arsenal...ma ci hanno copiato il Popopo mondiale :mbe:
a Marianella stava venendo un collasso sul 2-2
DioBrando
09-04-2008, 19:10
lol? perché prendi in giro DioBrando imitando MasterDany? :asd:
quando ci si becca online ci salutiamo sempre così ultimamente :asd:
DioBrando
09-04-2008, 19:13
lo sogno di notte Tanenbaum *.*
(:Prrr: )
cmq da amazon.com i libri che voglio comprare io li fanno pagare troppo >.> e il più delle volte per le spedizioni intercontinentali bisogna mettersi daccordo con il venditore che chiede una cifra spropositata T.T
amazon.uk e' gia meglio anche se noto che la community di amazon.com ha più libri :D
è un gran libro il Tanenbaum :)...purtroppo l'ho prestato e non ricordo granchè bene ma mi pare ci siano degli accenni anche su buffer overflow et similia oltre che protezioni wireless.
Questo per mjordan.
Su Amazon beh sì ci sn le tasse ecc. ma al cambio attuale con 1Euro = 1.55$ conviene di gran lunga.
Nella sezione UK purtroppo c'è la sterlina che ci penalizza :|
hauhauahauhauh l'ho letta solo ora T.T
mandami una tua foto cosi sogno anche te oltre tanenbaum rotfl:D :mc: :mc:
solo se sei bionda e hai una terza...ma non metto lower bounds sul QI :asd:
LMAO
Sostituisce proprio il primo. Se lo vuoi prendere evita di l'edizione italiana che costa sugli 80€ :mad:
Alla faccia del :eek:
DioBrando
09-04-2008, 19:49
X DioBrando: A me interessa qualcosa che non tratti la sicurezza in generale bensi a livello di codice (C, C++, Java).
C'è qualcosa? Ho l'impressione che molte volte quando si parli di sicurezza ci sono un sacco di libri che come target hanno il bimbo in preda ad una crisi di identità, a me servirebbe qualcosa di tecnico assai, che illustri i buffer overflow, per esempio, e tutte quelle pratiche "in codice" che in genere causano problemi di sicurezza e siano causa di exploit. C'è qualcosa che tu sappia?
EDIT: Se poi come target ha Unix, ancora meglio :)
Il libro di Zalewski è estremamente tecnico: vengono trattati gli attacchi basati sulla temporizzazione, PRNG, viene analizzato in modo molto approfondito l'intero stack TCP/IP e le relative debolezze (attacco di fingerprinting e contromisure), vengono menzionate le componentistiche del pc e come si possa trarne un proprio vantaggio, dalla mappatura degli interrupt e di come funzioni un particolare protocollo/bus di comunicazione (c'è l'howto di come costruire se non sbaglio una sorta di "cimice" che si colleghi alla LPT :D).
Vi è una parte logicamente dedicata all'algoritmica e matematica (anche se piuttosto marginale) e non prescinde dal trattare alcuni aspetti che probabilmente conoscete già (l'insicurezza delle reti wireless ad es.), ma garantisco che non è il classico testo che avete preso in mano sulla sicurezza.
Il primo capito si chiama: "Ti sento digitare" e sono convinto non abbiate mai visto trattata la tematica da questo punto di vista :)
C'è qualche porzione di codice, legata a Unix e scritta in C.
L'introduzione è stata affidata a Raul Chiesa, che non credo abbia bisogno di grandi presentazioni ^^
Altro libro che consiglio vivamente è:
Foundations of Security della Apress.
Il sottotitolo è "What Every Programmer Needs
to Know" :)
E in effetti soprattutto nelle prime due parti vengono enucleati oltre ai principi che un SWDesigner/architect/sviluppatore dovrebbe attenersi, vengono menzionate sia le best practices (quindi il lato "buono") sia le metodologie e attacchi utilizzati viceversa dai malintenzionati ( il lato "oscuro").
Ci sono anche esercizi alla fine di ogni capitolo.
Il terzo è dedicato alla crittografia.
Ora purtroppo devo andare, mi riservo di cercare qualcosa che sia + orientato allo sviluppo in un particolare linguaggio
Buona serata :)
Provengo dalla scuola di Richard Stevens, non so se mi intendi, che secondo me ha scritto i migliori libri della storia ;)
Il mio sogno invece sarebbe un'edizione moderna e rivisitata del famosissimo libro di Charles Petzold che non sia orientato a C# :cry:
Sì ho presente.
Credo che il Silberschatz (il libro di SO su cui ho studiato) si sia basato per la parte di Unix proprio sugli scritti di Stevens.
Sì ho presente.
Credo che il Silberschatz (il libro di SO su cui ho studiato) si sia basato per la parte di Unix proprio sugli scritti di Stevens.
Lo stesso libro che ho usato io. :D
m.distrutti
09-04-2008, 21:05
è un gran libro il Tanenbaum :)...purtroppo l'ho prestato e non ricordo granchè bene ma mi pare ci siano degli accenni anche su buffer overflow et similia oltre che protezioni wireless.
Questo per mjordan.
Su Amazon beh sì ci sn le tasse ecc. ma al cambio attuale con 1Euro = 1.55$ conviene di gran lunga.
Nella sezione UK purtroppo c'è la sterlina che ci penalizza :|
solo se sei bionda e hai una terza...ma non metto lower bounds sul QI :asd:
LMAO
per quanto riguarda i Sistemi Operativi lui e Alan Watt(credo si chiami cosi T.T purtroppo non sono molto ferreo con i nomi :) ) sono i must credo(anche perchè ho studiato solo i loro libri ihih); se non fosse per la mia attuale passione per la computer grafica mi sarei mangiato più libri a riguardo, le reti pure; argomenti davvero interessanti che col tempo ho trovato preziosissimi nello studio di algoritmi vari...
cmq per quanto riguarda amazon purtroppo anche se com teoricamente e' più conveniente di .uk, questo libro la comunity .uk non ce l'ha :S l'ho scovato solo nella .com americana e nella comunity brasialiana ahah, solo che per le spedizioni intercontinentali chiedono tipo 100$ chi lo vendo col CD >_<' e il rimanente lo vendono senza CD asd
un po obsoleto per il linguaggio a cui fa riferimento ma cmq un buon testo penso, lo cerco da 1 anno quasi sniff
http://ecx.images-amazon.com/images/I/61A4940D75L._SL500_BO2,204,203,200_PIlitb-dp-500-arrow,TopRight,45,-64_OU01_AA240_SH20_.jpg
per quanto riguarda i Sistemi Operativi lui e Alan Watt(credo si chiami cosi T.T purtroppo non sono molto ferreo con i nomi :) ) sono i must credo(anche perchè ho studiato solo i loro libri ihih); se non fosse per la mia attuale passione per la computer grafica mi sarei mangiato più libri a riguardo, le reti pure; argomenti davvero interessanti che col tempo ho trovato preziosissimi nello studio di algoritmi vari...
cmq per quanto riguarda amazon purtroppo anche se com teoricamente e' più conveniente di .uk, questo libro la comunity .uk non ce l'ha :S l'ho scovato solo nella .com americana e nella comunity brasialiana ahah, solo che per le spedizioni intercontinentali chiedono tipo 100$ chi lo vendo col CD >_<' e il rimanente lo vendono senza CD asd
un po obsoleto per il linguaggio a cui fa riferimento ma cmq un buon testo penso, lo cerco da 1 anno quasi sniff
http://ecx.images-amazon.com/images/I/61A4940D75L._SL500_BO2,204,203,200_PIlitb-dp-500-arrow,TopRight,45,-64_OU01_AA240_SH20_.jpg
Se è per quello allora un libro che tratta lo stesso argomento ed è sicuramente piu' nuovo è quello di Andrè LaMothe "Tricks of the 3D game programming gurus" pubblicato da Sams. Non l'ho mai letto ma pare abbia una buona reputazione.
m.distrutti
09-04-2008, 21:43
sisi ce l'ho già quello, anche il windows game programming che ha fatto e altri...
ringrazio la p2p per questo anche se comunque spenderci soldi penso ne valga la pena >_<' ma non ne ho cosi tanti per un libro ahah:D
poi tra l'altro usa una versione delle directX sotto la 8 se non erro, implementando gli algoritmi con le directDraw che ora non esistono
l'unico autore che scrive libri aggiornati con le directX e' Frank D. Luna che io sappia al momento
...
Altro libro che consiglio vivamente è:
Foundations of Security della Apress.
Il sottotitolo è "What Every Programmer Needs
to Know" :)
Questo sembra proprio quello che cercavo, una panoramica
("the big picture" :) ) sulla sicurezza dal punto di vista del programmatore.
Grazie mille!
Se è per quello allora un libro che tratta lo stesso argomento ed è sicuramente piu' nuovo è quello di Andrè LaMothe "Tricks of the 3D game programming gurus" pubblicato da Sams. Non l'ho mai letto ma pare abbia una buona reputazione.
Hmmm non sono grande fan di questi libri. Tendo a preferire le serie ShaderX e GPU Gems, perche' mostrano l'implementazione di singoli effetti, mentre libri come quello cercano di dare una visione di insieme di un engine 3d troppo rigida e "sovraingegnerizzata". Non ho letto questo in particolare comunque.
m.distrutti
10-04-2008, 13:00
Hmmm non sono grande fan di questi libri. Tendo a preferire le serie ShaderX e GPU Gems, perche' mostrano l'implementazione di singoli effetti, mentre libri come quello cercano di dare una visione di insieme di un engine 3d troppo rigida e "sovraingegnerizzata". Non ho letto questo in particolare comunque.
cosa intendi per troppo rigida e sovraingegnierizzata:S? pensavo che gli algoritmi base per un engine eran sempre quelli
GPU Gems non li trovo col CD mi sa che ne faro a meno T.T ahah, l'altra serie non la conosco :D
cdimauro
10-04-2008, 13:04
Ecco qui http://blogs.ugidotnet.org/Franny/archive/2007/09/12/88283.aspx cosa significa sovraingegnerizzazione... :stordita:
vBulletin® v3.6.4, Copyright ©2000-2025, Jelsoft Enterprises Ltd.