Hev87 ha scritto:
Vi ringrazio per le vostre risposte.
Come avrete notato, sono piuttosto ignorante in campo di programmazione e capiterà spesso, almeno per i primi tempi, sentirmi adottare termini inadeguati e difficilmente comprensibili.
Ho provato ad informarmi sul web prendendo come spunto le indicazioni contenute nelle vostre risposte, tuttavia l'unico risultato che ottengo è un allucinante mal di testa dopo aver tentato invano di comprendere il linguaggio tecnico con cui si esprimono gli esperti
Leggendo le vostre risposte ho capito che ciò che malamente definivo "velocità di lettura" è in realtà la velocità di esecuzione.
Scrivendo un codice del genere ad esempio:
static void Main()
{ DateTime Beg = DateTime.Now;
for (z = 0; z < 1000000000; z++)
{
n++;
}
DateTime End = DateTime.Now;
Console.WriteLine(" tempo impiegato = {1} ", End-Beg);
Console.ReadLine();
}
L'Output sarà " tempo impiegato = 00:00:06.199488 ";
L'obiettivo è ridurre il più possibile quel "06"...
migliorabile, dicevi che è possibile incrementare la velocità d'esecuzione tramite strutture dati di supporto. Cosa sarebbero di preciso queste strutture? Come si realizzano?
Ringrazio per la disponibilità e la pazienza
A mio giudizio per valutare devi prima partire da una considerazione di base; la CPU di un computer può eseguire un algoritmo descritto sia come linguaggio "interpretato" sia come linguaggio "compilato".
La "lettura di codice" della quale tu parli è proprio la fase di interpretazione del codice tipica dei linguaggi interpretati. Esiste un sorgente del programma in formato testuale, esiste un programma apposito che si chiama interprete, l'interprete esegue una continua scansione del sorgente e quindi "mette in opera" le varie istruzioni da lui incontrate. Se tu scrivi 1 miliardo di cicli for, l'interprete legge e interpreta 1 miliardo di volte quel codice.
Attenzione però che qui parliamo di tecnologie di almeno 30 anni orsono, l'esempio che mi viene in mente adesso è quello del GWBasic del DOS. Linguaggi interpretati più moderni mettono in pratica delle tecniche di ottimizzazione, tokenizzazione, decodifica preventiva e così via.
La "compilazione" del codice è questione radicalmente diversa; nei computer la CPU esegue solo e unicamente un suo particolare linguaggio, l'assembler, fatto di istruzioni che nulla hanno in comune con gli usuali linguaggi di programmazione. La CPU carica dalla memoria tale codice assembler e lo esegue. Esistono degli algoritmi molto complessi detti "compilatori", che permettono di convertire un linguaggio di programmazione usuale nel corrispondente linguaggio assembler. I compilatori mettono in pratica una completa destrutturazione del codice, ovvero fanno "sparire" i cicli for, i cicli while, gli assegnamenti e così via. Il tuo ciclo for da 1 a 1 miliardo viene sostituito con un contatore che viene via via incrementato, poi confrontato con il valore limite fisso di 1 miliardo, quindi si passa attraverso una particolare istruzione di "salto condizionato", che è una sorta di GOTO del BASIC, e il ciclo ricomincia, oppure salta alla fine se si è arrivati a 1 miliardo.
A voler essere precisi, anche l'assembler sarebbe un linguaggio "interpretato", nel senso che la CPU stessa costituisce un algoritmo di interpretazione ed esecuzione "scolpito" nel silicio, quindi velocissimo. La base di tale opera è costituita da degli esecutori, che non sono altro che automi a stati finiti realizzati nel silicio mediante gate logici, che non operano attraverso un linguaggio di programmazione bensì attraverso molteplici (e contorte) transizioni di stato.
Per quanto ti riguarda, per il tuo voler fare il ciclo il più veloce possibile, lo devi fare direttamente in linguaggio assembler. Oppure usi il linguaggio C++ , che è quello che "codifica" nel modo più sgamato possibile, a volte il compilatore C++ crea delle vere e proprie opere d'arte di ottimizzazione, e per fare meglio del compilatore C++ ci deve mettere mano un programmatore assembler decisamente skillato.
Se vuoi andare MOLTO veloce, allora non ti rimane che programmare a livello di gate logici; devi fare affidamento a potenti logiche programmabili (a questo punto neanche una CPU ti basta per i tuoi scopi), devi descrivere dei circuiti di calcolo a livello di gate o a livello di comportamento (behavioral), devi sintatizzarli dentro ad una FPGA o ASIC, quindi li puoi lanciare a velocità mai viste prima.
Una simile tecnologia ad esempio torna utile nel momento in cui si vogliano implementare particolari algoritmi a velocità estrema, come algoritmi di cifratura, generazione di CRC, generazione di numeri pseudocasuali, cracking di password brute force e così via. La funzione la si realizza su silicio, va velocissima, e costa un botto!!
Spero di essere stato sufficientemente esaustivo.