Som sa rozhodol, že vám tu niečím prispejem - som sa hral s jednou úlohou. Samozrejme, že to ako správny egoista nerobím nezištne, ale očakávam, že mi tu niekto vynadá aký je to trápny kód a napíše lepšie riešenie, z ktorého sa budem môcť priučiť, a ktoré budem môcť prekonávať
Inak, nejako mi nefunguje nahrávanie súborov - neviem či je to vo mne alebo vo vás, tak sa na to mrkniteCode:/* * Súbor: aRRa.c * Dátum: 14.8.2009 * Autor: m-> 29 * Názov: Prevod číslic * Popis: Prevádza čísla medzi arabským a rímskym zápisom. */ #include <stdio.h> #include <stdlib.h> #include <string.h> #include <ctype.h> #define ROMAN_SIZE 16 #define ROMAN_MAX 3999 typedef struct { unsigned value; char str[ROMAN_SIZE]; } roman_t; enum romeDigits {I, V, X, L, C, D, M}; const struct { unsigned value; char c; } romeDigits[] = { [I] = {1, 'I'}, [V] = {5, 'V'}, [X] = {10, 'X'}, [L] = {50, 'L'}, [C] = {100, 'C'}, [D] = {500, 'D'}, [M] = {1000, 'M'}, }; /** * Prevedie číslo z arabskej do rímskej sústavy. */ roman_t roman(int x) { if(x < 0) { return (roman_t) {-1, "NaRN"}; } // Not a Roman Number if(x == 0) { return (roman_t) {0, "nullae"}; } // zero if(x > ROMAN_MAX) { return (roman_t) {-1, "infinity"}; } // !!! infinity roman_t result = { .value = x, .str = "", }; char *str = (char *)&result.str; unsigned y = 1, digit = 0, order = 0; while(x/y > 10) { y *= 10; order += 2; } while(x > 0) { digit = x/y; x %= y; y /= 10; if(digit <= 3) { for(unsigned i=0; i<digit; i++) { *str++ = romeDigits[order].c; } } else if(digit == 4) { *str++ = romeDigits[order].c; *str++ = romeDigits[order+1].c; } else if(digit <= 8) { *str++ = romeDigits[order+1].c; for(unsigned i=5; i<digit; i++) { *str++ = romeDigits[order].c; } } else if(digit == 9) { *str++ = romeDigits[order].c; *str++ = romeDigits[order+2].c; } order -= 2; } return result; } static int romeChar2digit(char c) { switch(toupper(c)) { case '\0': return 0; case 'I': return 1; case 'V': return 5; case 'X': return 10; case 'L': return 50; case 'C': return 100; case 'D': return 500; case 'M': return 1000; default: return -1; } } int arabic(const char *str) { // !!! CLL != 200 int result = 0, max = romeDigits[M].value; int digits[ROMAN_SIZE] = {0}; for(unsigned i=0; str[i] != '\0'; i++) { if((digits[i] = romeChar2digit(str[i])) == -1) { return -1; } } for(unsigned i=0; digits[i]; i++) { if(digits[i] < digits[i+1] && digits[i+1]/digits[i] != 5 && digits[i+1]/digits[i] != 10) { return -1; } if(str[i]==str[i+1] && str[i+2]==str[i+3] && str[i]==str[i+2] && str[i]==str[i+4]) { return -2; } if(digits[i] > max) { return -3; } if(digits[i]==digits[i+1] && (digits[i]+digits[i+1]==romeDigits[X].value || digits[i]+digits[i+1]==romeDigits[C].value || digits[i]+digits[i+1]==romeDigits[M].value)) { return -4; } if(digits[i] < digits[i+1]) { result = result - digits[i] + digits[i+1]; if(digits[i+1] > max) { return -3; } max = (unsigned)digits[i++] >> 1; } else { result += digits[i]; max = digits[i+1]; } } // if(strcmp(roman(result).str, str) != 0) { return -29; } return result; } int main(void) { // unsigned input = 0; char romeNum[ROMAN_SIZE]; FILE *fin = fopen("data.txt", "r"); while(fscanf(fin, "%16[IVXLCDMivxlcdm]", romeNum) == 1) { fgetc(fin); // scanf("%u", &input); // puts(roman(input).str); printf("%15s = %d\n", romeNum, arabic(romeNum)); } return EXIT_SUCCESS; }![]()



Reply With Quote
