[C/C++] Esperimento di "programmazione distribuita"
Siccome mi trovo in una specie di vacanza forzata, essendomi laureato da poco e non avendo ancora trovato lavoro, ho un po' voglia di giocare. Ecco quindi che voglio dare inizio ad una specie di esperimento di "programmazione distribuita". Le regole sono molto semplici: si deve partire da uno dei codici precedentemente postati (possibilmente l'ultimo) e modificarlo come si desidera. L'unica condizione è che il codice risultante deve essere corretto e quindi compilabile e per quanto possibile privo di errori. Ecco quindi il primo codice. Come da tradizione, non poteva che essere un Hello World.
P.S. Il codice iniziale è in C, ma si può anche passare al C++ se lo si preferisce. Eviterei il passaggio ad altri linguaggi come Java o Python, volendo si possono fare poi altri esperimenti simili in altri linguaggi se avrà successo.
#include <stdio.h>
int main(void)
{
puts("Ciao Mondo!\n");
return 0;
}
P.S. Il codice iniziale è in C, ma si può anche passare al C++ se lo si preferisce. Eviterei il passaggio ad altri linguaggi come Java o Python, volendo si possono fare poi altri esperimenti simili in altri linguaggi se avrà successo.
Risposte
ciao apatriarca 
che si fa per passarsi il tempo
vediamo:
ho fatto un merge non toccanto la tua parte.
Output:
avanti il prossimo
che si fa per passarsi il tempo
vediamo:
#include <stdio.h>
int main(void){
int i,j;
int M = 6;
int T = 0;
/* spazi binari */
i=0;
while(i<M){
T = T + (1<<(M-1-i));
j=0;
while(j<M){
if(T & (1<<j)) printf("*");
else printf(" ");
j++;
}
/*apatriarca*/
puts("Ciao Mondo!\n");
i++;
}
return 0;
}ho fatto un merge non toccanto la tua parte.
Output:
*Ciao Mondo!
**Ciao Mondo!
***Ciao Mondo!
****Ciao Mondo!
*****Ciao Mondo!
******Ciao Mondo!
avanti il prossimo
Ma scrivere i "Ciao Mondo" non è poi così interessante.. Scriviamo qualche numero..
#include <stdio.h>
#define MAX_NUMERI 6
char *numeri[MAX_NUMERI] = { "Uno!", "Due!", "Tre!", "Quattro!", "Cinque!", "Sei!" };
int main(void){
int i,j;
int M = MAX_NUMERI;
int T = 0;
/* spazi binari */
i=0;
while(i<M){
T = T + (1<<(M-1-i));
j=0;
while(j<M){
if(T & (1<<j)) printf("*");
else printf(" ");
j++;
}
/*apatriarca*/
puts(numeri[i]);
i++;
}
return 0;
}
Randomizziamo un po' i numeri stampati. Devio in C++ perché fare una cosa del genere con array di caratteri è un suicidio (però almeno l'interfaccia è C-like).
Edit: Corretto errore.
Edit: Corretto errore.
#include <iostream>
#include <string>
#include <algorithm>
#include <cstdio>
#include <ctime>
#include <cstdlib>
std::string nToString2(long n)
{
static std::string units[] = {"uno", "due", "tre", "quattro", "cinque",
"sei", "sette", "otto", "nove"};
static std::string teens[] = {"dieci", "undici", "dodici", "tredici",
"quattordici", "quindici", "sedici",
"diciassette", "diciotto", "diciannove"};
static std::string tenths[] = {"venti", "trenta", "quaranta", "cinquanta",
"sessanta", "settanta", "ottanta", "novanta"};
static std::string hundred = "cento";
static std::string thousand = "mille";
static std::string thousands = "mila";
const long Thousand = 1000;
const long Hundred = 100;
const long Twenty = 20;
const long Ten = 10;
if (n == 0) {
return "";
} else if (n >= 2 * Thousand) {
return nToString2(n / Thousand) + " " + thousands + " "
+ nToString2(n % Thousand);
} else if (n >= Thousand) {
return thousand + " " + nToString2(n % Thousand);
} else if (n >= 2 * Hundred) {
return nToString2(n / Hundred) + " " + hundred + " "
+ nToString2(n % Hundred);
} else if (n >= Hundred) {
return hundred + " " + nToString2(n % Hundred);
} else if (n >= Twenty) {
return tenths[n / Ten - 2] + " " + nToString2(n % Ten);
} else if (n >= Ten) {
return teens[n - Ten];
} else {
return units[n - 1];
}
}
std::string nToString(long n)
{
static std::string zero = "zero";
static std::string minus = "meno";
if (n == 0) {
return zero;
} else if (n < 0) {
return minus + " " + nToString2(-n);
} else {
return nToString2(n);
}
}
// Ricordati di chiamare free().
char * nToChars(long n)
{
std::string string = nToString(n);
char * c = (char*)malloc((string.size() + 1) * sizeof *c);
std::copy(string.begin(), string.end(), c);
c[string.size()] = 0;
return c;
}
int main(void){
int i,j;
long n;
const int M = 20;
int T = 0;
srand(time(0));
/* spazi binari */
i=0;
while(i<M){
T = T + (1<<(M-1-i));
j=0;
while(j<M){
if(T & (1<<j)) printf("*");
else printf(" ");
j++;
}
/*apatriarca*/
n = rand() % 1000 - 500;
char * c = nToChars(n);
puts(c);
free (c);
i++;
}
return 0;
}
Eppure.. il corrispondente codice in C non è molto più complicato o lungo. Si deve solo ricorrere ad una stringa di dimensione fissata, sufficiente a contenere il numero, e utilizzare strcat al posto della somma. Ho riscritto il programma in una forma un po' diversa e ho utilizzato le stringhe del C (stringhe non molto efficienti per questo tipo di utilizzo - non che std::string sia più efficiente in realtà..).. Ho eliminato la possibilità di avere numeri negativi, ma non modifica la sostanza.
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
const char * unitsName(long n) {
assert(n >= 0 && n < 10);
static const char * units[] = {"zero ", "uno ", "due ", "tre ", "quattro ",
"cinque ", "sei ", "sette ", "otto ",
"nove "};
return units[n];
}
const char * teensName(long n) {
assert(n >= 10 && n < 20);
static const char * teens[] = {"dieci ", "undici ", "dodici ", "tredici ",
"quattordici ", "quindici ", "sedici ",
"diciassette ", "diciotto ", "diciannove "};
return teens[n - 10];
}
const char * lessThanHundredName(long n) {
assert(n >= 0 && n < 100);
static char buffer[20] = "";
buffer[0] = '\0';
if (n < 10) {
return unitsName(n);
} else if (n < 20) {
return teensName(n);
}
static const char * tenths[] = {0, 0, "venti ", "trenta ", "quaranta ",
"cinquanta ", "sessanta ", "settanta ",
"ottanta ", "novanta "};
const long tenth = n / 10;
const long unit = n % 10;
if (unit == 0) {
return tenths[tenth];
} else {
strcat(buffer, tenths[tenth]);
strcat(buffer, unitsName(unit));
return buffer;
}
}
const char * lessThanThousandName(long n) {
assert(n >= 0 && n < 1000);
static char buffer[40] = "";
buffer[0] = '\0';
if (n < 100) {
return lessThanHundredName(n);
}
if (n > 199) {
strcat(buffer, unitsName(n / 100));
}
strcat(buffer, "cento ");
if (n != 100) {
strcat(buffer, lessThanHundredName(n % 100));
}
return buffer;
}
const char * lessThanMillionName(long n) {
assert(n >= 0 && n < 1000000);
static char buffer[100] = "";
buffer[0] = '\0';
if (n < 1000) {
return lessThanThousandName(n);
}
if (n < 2000) {
if (n != 1000) {
strcat(buffer, "mille ");
strcat(buffer, lessThanThousandName(n - 1000));
} else {
return "mille ";
}
} else {
const long thousands = n / 1000;
const long rest = n % 1000;
strcat(buffer, lessThanThousandName(thousands));
strcat(buffer, "mila ");
if (rest != 0) {
strcat(buffer, lessThanThousandName(rest));
}
}
return buffer;
}
const char * nToChars(long n) {
return lessThanMillionName(n);
}
int main(void){
int i,j;
long n;
const int M = 20;
int T = 0;
srand(time(0));
/* spazi binari */
i=0;
while(i<M){
T = T + (1<<(M-1-i));
j=0;
while(j<M){
if(T & (1<<j)) printf("*");
else printf(" ");
j++;
}
/*apatriarca*/
n = rand() % 1000000;
puts( nToChars(n) );
i++;
}
return 0;
}