2012-04-06 52 views
7

我正在爲C(第一編程課程)中的課程做家庭作業。 分配的一部分是編寫代碼,以便用戶輸入長達9位數的數字,並且程序需要確定該數字是「增加」/「真正增加」/「減少」/「真正減少」/ 「增加和減少」/「真正減少和真正增加」/「不減少和不增加」。 (共7個選項)從C中抽取個別數字C

由於這是我們的第一個任務我們不允許使用任何東西,除了什麼在課堂上講授:

做,而對於,while循環,否則,如果,如果, 突破,繼續 scanf函數,printf的,取模,以及基本的運營商

(我們不能用任何庫除了爲stdio.h中)

就是這樣。我不能使用數組或getchar或任何這些東西。我可以用來接收用戶輸入的唯一功能是scanf

到目前爲止,我已經用流程圖和所有內容編寫了算法,但我需要將用戶的輸入分隔爲不同的數字。

例如,如果用戶輸入「1234 ...」,我想在a中保存1,在b中保存2,等等,然後比較所有數字以確定它們是否全部相等(增加和減少)還是a> b> c ...(減少)等等。

我知道如何通過使用%和/運算符來分隔每個數字,但我無法弄清楚如何將這些值「保存」到一個變量中,以便稍後用於比較。

這是我到目前爲止有:

printf("Enter a positive number : "); 

do { 
    scanf ("%ld", &number); 
    if (number < 0) { 
     printf ("invalid input...enter a positive integer: "); 
     continue; 
    } 
    else break; 
} while (1); 

while (number < 0) { 
    a = number % 10; 
    number = number - a; 
    number = number/10; 
    b = a; 
} 
+2

等等,他們希望您將一個數字分成「最多9位」數字,但他們不會讓您使用數組?多數民衆贊成在那...這只是殘酷! – 2012-04-06 14:58:42

+0

這只是第一部分...另一部分與Goldbach理論有關,用戶輸入任何數字最多9位數字,並且計算機輸出第一個加上該數字的素數。同樣的限制,以及 – nofe 2012-04-06 15:02:43

+2

我不明白你的增加與真正增加的概念。什麼是「增加和減少」與「真正減少和真正增加」。請說明你的代碼應該如何分類輸入。 – abelenky 2012-04-06 15:24:52

回答

4

爲什麼不對其進行掃描的文字(string)?然後你可以通過數組偏移來訪問它們,從ASCII字符代碼中減去48的偏移量。您可以使用ctype.h中的isdigit來驗證該字符是數字。


編輯

因爲你的教授到位,令人難以置信的心不在焉限制:

#include <stdio.h> 

int main() 
{ 
    int number; 
    printf("Enter a positive number: "); 

    do 
    { 
    scanf ("%ld", &number); 
    if (number < 0) 
    { 
     printf ("invalid input...enter a positive integer: "); 
     continue; 
    } 
    else break; 
    } while (1); 

    int a = -1; 
    int b = -1; 
    int c = -1; 
    int d = -1; 
    int e = -1; 
    int f = -1; 
    int g = -1; 
    int h = -1; 
    int i = -1; 

    while (number > 0) 
    { 
    if (a < 0) a = number % 10; 
    else if (b < 0) b = number % 10; 
    else if (c < 0) c = number % 10; 
    else if (d < 0) d = number % 10; 
    else if (e < 0) e = number % 10; 
    else if (f < 0) f = number % 10; 
    else if (g < 0) g = number % 10; 
    else if (h < 0) h = number % 10; 
    else if (i < 0) i = number % 10; 

    number /= 10; 
    } 

    /* Printing for verification. */ 

    printf("%i", a); 
    printf("%i", b); 
    printf("%i", c); 
    printf("%i", d); 
    printf("%i", e); 
    printf("%i", f); 
    printf("%i", g); 
    printf("%i", h); 
    printf("%i", i); 

    return 0; 
} 

末的有效數字將是積極的,所以這些都是你驗證以滿足你的不同條件。

+2

我列出了我對上述任務的限制......問「爲什麼不這樣做」或者這是無關緊要的。你不妨問我爲什麼要學習C(爲什麼不是Java?C++?)。我是因爲這就是我的大學對我的要求 – nofe 2012-04-06 15:04:16

+2

如果你可以掃描整數,你可以掃描字符。數組偏移量基本上是加法的,這符合基本操作符的限制。 – 2012-04-06 15:06:12

+0

我可以掃描字符,你說得對。你可以解釋如何做一個數組偏移而不使用數組(不知道數組是什麼),因爲isdigit我不能使用除stdio.h之外的任何其他庫,但這沒關係,因爲我不需要驗證字符確實是數字,用戶只輸入整數。 – nofe 2012-04-06 15:11:09

1

讓我們假設你有這個號碼23654

23654 % 10000 = 2 and 3654 
3654 % 1000 = 3 and 654 
654 % 100 = 6 and 54 
54 % 10 = 5 and 4 
4 

這樣你就可以得到所有的數字。當然,你必須知道該數字是否大於10000,1000,100或10,才能知道第一個除數。

玩sizeof獲得整數的大小,以避免巨大的如果...else語句

編輯:

讓我們來看看

if (number>0) { 
    // Well, whe have the first and only digit 
} else if (number>10) { 
    int first_digit = number/10; 
    int second_digit = number % 10; 
} else if (number>100) { 
    int first_digit = number/100; 
    int second_digit = (number % 100)/10; 
    int third_digit = (number % 100) % 10; 
} ... 

等等,我想

+0

我需要把它放到一個循環中,因爲我需要處理多達9位數字。此外,我想「保存」這些數字的某處或將它們分配給變量,以便我可以將它們用於我的比較 – nofe 2012-04-06 15:06:14

+0

不能使用sizeof ....巨大的if-else語句很好 – nofe 2012-04-06 15:08:24

0

下面是純C工作示例:

#include <stdio.h> 

unsigned long alePow (unsigned long int x, unsigned long int y); 

int main(int argc, const char* argv[]) 
{ 
    int enter_num, temp_num, sum = 0; 
    int divisor, digit, count = 0; 

    printf("Please enter number\n"); 
    scanf("%d", &enter_num); 

    temp_num = enter_num; 

    // Counting the number of digits in the entered integer 
    while (temp_num != 0) 
    { 
     temp_num = temp_num/10; 
     count++; 
    } 

    temp_num = enter_num; 

    // Extracting the digits 
    printf("Individual digits in the entered number are "); 
    do 
    { 
     divisor = (int)(alePow(10.0, --count)); 
     digit = temp_num/divisor; 
     temp_num = temp_num % divisor; 

     printf(" %d",digit); 
     sum = sum + digit; 
    } 
    while(count != 0); 

    printf("\nSum of the digits is = %d\n",sum); 

    return 0; 
} 


unsigned long alePow(unsigned long int x, unsigned long int y) { 

    if (x==0) { return 0; } 
    if (y==0||x==1) { return 1; } 
    if (y==1) { return x; } 
    return alePow(x*x, y/2) * ((y%2==0) ? 1 : x); 
} 
+0

謝謝,其中一些有用。我不想總結數字,但我想在它們之間進行比較。我也無法使用math.h – nofe 2012-04-06 15:15:13

+0

沒有使用math.h更新,看看alePow函數;) – aleroot 2012-04-06 15:21:35

1

這是愚蠢的要求你做沒有數組的循環---但是t帽子是你老師的錯,不是你的。

話雖這麼說,我會做這樣的事情:

char c; 
while (1) { 
    scanf("%c", &c); 
    if (c == '\n') /* encountered newline (end of input) */ 
     break; 
    if (c < '0' || c > '9') 
     break;  /* do something to handle bad characters? */ 
    c -= '0'; 
    /* 
    * At this point you've got 0 <= c < 9. This is 
    * where you do your homework :) 
    */ 
} 

這裏的訣竅是,當你鍵入數字到程序中,你在同一時間的所有發送緩衝區的一次,而不是一個字符。這意味着第一個scanf將一直阻塞,直到整個字符串(即「123823」或其他)與新行字符('\ n')一起到達。然後這個循環在閒暇時分析該字符串。

編輯爲了測試數字的增加/減少,你可能會認爲你需要存儲整個字符串,但事實並非如此。只是定義一些額外的變量需要記住的重要信息,如:

int largest_digit_ive_seen, smallest_digit_ive_seen, strict_increasing_thus_far; 

等等,等等

+0

謝謝,我實際上已經知道如何驗證輸入有效性,但你說服我考慮再次使用char。解析是什麼意思? – nofe 2012-04-06 15:17:31

+1

「解析」表示分析(粗略)。 'char'數據類型與'int'類似,但較小:它只能處理-128到127範圍內的數字(但對於只能是0-9的單個數字,這是很好的)。我使用'char'的原因是因爲我想使用'%c',它只能讀取一個數字。但'scanf'要求你使用'char'來使用'%c'。除此之外,它可能是'int'而不是'char' ---它只是存儲一個數字。 – 2012-04-06 15:23:44

0

我建議循環展開(忽略這個詞,如果你不知道這一點)。

int a=-1, b=-1, c=-1, d=-1, e=1, f=-1, g=-1, h=-1, i=-1; // for holding 9 digits 
int count = 0; //for number of digits in the given number 


if(number>0) { 
i=number%10; 
number/=10; 
count++; 
} 

if(number>0) { 
h=number%10; 
number/=10; 
count++; 
} 

if(number>0) { 
g=number%10; 
number/=10; 
count++; 
} 
.... 
.... 
/* All the way down to the storing variable a */ 

現在,你知道數字的數量(變量數),它們存儲在哪個變量中。現在你有所有的數字,你可以檢查他們的「減少」,「增加」等很多如果!

鑑於所有條件,我無法真正想到更好的解決方案。

+0

好吧,我想我可以用一個大循環來削減角落,但是根據你所說的,我必須這樣做。我已經擁有了自己,我只是希望有一條捷徑。謝謝 – nofe 2012-04-06 15:24:42

+0

因爲你的條件使得爲此寫一個更好的解決方案真的很難:) – 2012-04-06 15:26:54

+0

@nofe你可以使用循環,你幾乎肯定應該在這裏使用循環! 'int a,b,c,d ...'和'int digits [9]'是一樣的,所以如果你有一個數組,那麼你可以很容易地遍歷所有的數字。 – Kiril 2012-04-06 15:33:49

1

既然你只需要比較連續的數字,有一種優雅的方式來做到這一點沒有數組:

int decreasing = 2; 
int increasing = 2; 

while(number > 9) 
{ 
    int a = number % 10; 
    int b = (number/10) % 10; 

    if(a == b) 
    { 
    decreasing = min(1, decreasing); 
    increasing = min(1, increasing); 
    } 
    else if(a > b) 
    decreasing = 0; 
    else if(a < b) 
    increasing = 0; 

    number /= 10; 
} 

在這裏,我們通過數走(由10分),直到只有一個手指保持。我們在decreasingincreasing-2表示真正增加/減少,表示1意味着增加/減少,而0意味着不增加/減少。

在每一步,a是個位數,b是十位。然後,根據ab之間的比較,我們更改increasingdecreasing

最後,應該很容易將increasingdecreasing的值轉換爲您想要的最終答案。

注意:函數min返回其2個參數中較小的一個。您應該能夠編寫自己的語句,或者用if語句或條件替換那些行。