זקוק לעזרה, לולאות While וSwitch Case בC. - תכנות - HWzone פורומים
עבור לתוכן
  • צור חשבון

זקוק לעזרה, לולאות While וSwitch Case בC.


Stoned Junglist

Recommended Posts

שלום.

אני צריך עזרה בשתי התוכניות הנ"ל:


int main()
{
int num,i,count;
do
{
scanf("%d",&num);
}while(num<0);
while(num!=1)
{
if((num%2)==0)
{
num=num/2;
count++;
printf("Next value is: %d\n",num);
}
else
{
num=(num*3)+1;
count++;
printf("Next value is: %d\n",num);
}
}
printf("Final value %d, number of steps %d\n",num,count);
return 0;
}

למעשה בתרגיל הנ"ל - אני רוצה לקלוט מספר בלולאה , אם הוא זוגי לעשות על פעולה חשבונית ואם הוא אי זוגי לעשות עליו פעולה חשבונית, ולעצור תלולאה שהמספר מגיע ל1. בסוף אני צריך לכתוב כמה צעדים ואת המספר הסופי שהוא 1. בתרגיל אני צריך לעשות לולאה שאם הקלט הוא לא מספר שלם וחיובי אז צריך לבקש מהמשתמש להקליד קלט חדש שוב ולהמשיך תלולאה עד שיקליד קלט תקין שהוא מספר חיובי ושלם. אך אינני מצליח.. מה הבעיה בקוד הנ"ל?

====


#include <stdio.h>
int main()
{
char selection;
scanf("%d",&selection);
switch(selection)
{
case 1:
func1;
break;
case 2:
func2;
break;
case3:
func3;
break;
case4:
func4;
break;
default:
break;
}
}

אוקי הקוד הנ"ל- אני רוצה לעשות תפריט של בחירה, ובחירה 1,2,3,4 כל אחד מהם יכנס לפונקציה שונה (לא עקרוני מה הפונקציה כרגע היא לא הבעיה) למעשה הבעיה שלי היא שאני לא מצליח ליצור לולאה שכל הזמן שהוא יכנס לdefault (מספר שהוא לא 1,2,3,4) הוא יבקש מהמשתמש שיקליד פלט תקין שוב עד שיקליד פלט תקין.

תודה רבה. סליחה שזה כל כך ארוך.

קישור לתוכן
שתף באתרים אחרים

  • תגובות 51
  • נוצר
  • תגובה אחרונה

תרגיל א:

לא אתחלת את count - הוא מכיל ערך אקראי במקום 0 בתחילת התכנית.

חוץ מזה, המשתנה i מיותר (אתה לא משתמש בו, לא יודע אם זה משנה או לא).

תרגיל ב:

תשתמש בלולאה while עם משתנה עזר, כך שאם אתה מגיע ל-default הוא יקבל ערך אחד, ובכל שאר המקרים יקבל ערך אחר.

נ.ב. נסה לדייק יותר בבעיה בתכנית, במקום לומר "אני לא מצליח".

קישור לתוכן
שתף באתרים אחרים

לגבי התרגיל הראשון, יש לך כמה בעיות:

- את הקליטה של num אתה עושה רק פעם אחת מחוץ ללולאה ולא ממשיך לקלוט ככה שבעצם אתה ממשיך לבדוק שוב ושוב בלולאה את אותו המספר. אחרי ה if\else בגוף הלולאה אתה צריך לקלוט מס' חדש.

- לגבי הקליטה של המס': כרגע אתה בודק רק אם הוא קטן מאפס. אם המשתמש מכניס מספר עם שבר (נקודה עשרונית) או כל קלט אחר אתה בבעיה. בעיקרון scanf מחזיר את מס' המשתנים שנקלטו בהצלחה ככה שאם המשתמש הכניס משהו לא חוקי יוחזר 0. אתה יכול לנסות את זה אבל scanf יכול להיות בעייתי כי הוא עלול לא לנקות את הקלט הלא חוקי ואתה יכול להתקע בלולאה אינסופית. אתה יכול אולי לעשות משהו כזה:

int num = 0;
double d;
char buff[256];

do
{
printf("Please enter a (valid) number: ");
fgets(buff, 256, stdin);
d = atof(buff);
num = (int)d;
}
while((d!=num) || num <= 0);

fgets קולטת את הקלט כמחרוזת. atof ממירה את הקלט לשבר עשרוני והשורה הבאה ממירה את d ל int ומציבה ב num. אם d הוא מספר שלם אז d יהיה שווה ל num. במידה והקלטת לא הצליח num יהיה 0. ככה בתנאי של הלולאה אתה מכסה שבר עשרוני, קלט לא מוצלח ומס' שלילי. רק שים לב שאם אתה מכניס מס' ואז תו לא חוקי כלשהו הוא יקלוט את המס' שלפניו כקלט חוקי.

- אתה צריך להציב 0 ב count לפני שאתה משתמש בו.

- את השורות count++ וה printf שאחריה אתה יכול להוציא מה if/else במקום לכתוב אותן פעמיים הרי הן יתבצעו בכל מקרה.

לגבי התרגיל השני: אתה רוצה שבכל מקרה תהיה לולאה (אפשרות לחזור שוב לתפריט) או רק במקרה של קלט לא חוקי?

קישור לתוכן
שתף באתרים אחרים

סליחה אם לא היתי ברור.

תודה, בתרגיל 2 אני רוצה שבכל מקרה של קלט לא חוקי הלולאה תמשיך לפעול ולבקש בחירה בין 1 עד ל3, כאילו להכריח את המשתמש להכניס קלט חוקי (כלומר בין 1 ל-4 כולל). וכאשר המשתמש יבחר 1, 2 או 3 וסיים את התוכנית ב1, 2, 3 הוא יחזור לתפריט . והתוכנית תעצר רק שתגיע ל4.

שניצל , השתמשתי במשתנה עזר אך קיבלתי לולאה אינספית שכל הזמן מבקש ממני להקליד קלט( שהקלדתי קלט לא חוקי כדאי לבדוק אם התוכנה שלי פועלת) ואפילו שהקלדתי 1 או 4 בשביל לבדוק עם הוא נכנס לSWITCHCASE הוא ביקש המשיך לבקש קלט. להל"ן התוכנה שלי:


#include <stdio.h>
int main()
{
char selection;
int i;
scanf("%d",&selection);
do
{
scanf("%d",&selection);
switch(selection)
{
case 1:
i=0;
printf("lol1");
break;
case 2:
i=0;
printf("lol2");
break;
case 3:
i=0;
printf("lol3");
break;
case 4:
i=0;
printf("lol4");
break;
default:
i=1;
break;
}
}
while(i=1);
}

למעשה הבעיה בתרגיל 2 - הינה שאני לא מצליח לצור לולאה שתמשיך כל עוד הקלט לא חוקי וגם- 1 עד 3, ותפסיק שהקלט חוקי הינו 4. ולמעשה ב4 התוכנה תסתיים.

==

בקשר לתרגיל 1 , הבנתי בערך את הקטע עם המחרוזת מכיוון שעדין לא למדתי מחרוזות, הבעיה היחידה שלי היא- לא הבנתי איך אתה מכסה את הבעיה במקרה שהקלט הוא תו (a לדוגמא) והאם יש פתרון אחר, בלי מחרוזות לכסות את כל האפשרויות במקרה של קלט לא תקין?

תודה רבה.

עריכה-תרגיל אחד נסיון=> בהרצת תוכנה מקבל Bus error. מה זאת אומרת?


int main()
{
char num;
double d;
int count=0;
scanf("%d",&num);
do
{
scanf("%d",&num);
if((num%2)==0)
{
num=num/2;
}
else
{
num=(num*3)+1;
}
count++;
printf("Next value is: %d\n",num);
d=num;
num=(int)d;
}
while(num<0||(num!=d));
printf("Final value %d, number of steps %d\n",num,count);
return 0;
}

עריכה 2-שניצל עשיתי כמו שאמרתה ,ובתרגיל 2 ושהקלדתי פלט שגוי לבדוק את תקינות התוכנה קיבלתי Bus error. =\

קישור לתוכן
שתף באתרים אחרים

יש לי עוד שאלה .

אני צריך לתכנת תוכנה ש"קוראת" כל תו במשפט שהמשתמש מכניס, וכותבת כמה a יש וכמה אותיות חוץ מa יש במשפט.

אך אין לי מושג מאיפה להתחיל, איך אני בגלל "קורא" כל תו במשפט? :nixweiss: אני עובד עצות. אנא עזרו לי .. תודה :s05:

קישור לתוכן
שתף באתרים אחרים

ככה אתה קורא תווים בודדים:

char ch;
scanf("%c", &ch);

אופציה נוספת היא לקרוא את כל המשפט לתוך מחרוזת במכה באמצעות fgets ואז לעבור עליו.

מה זאת אומרת לעבור עליו?

סליחה אבל כנראה לא הבנתה, התכוונתי נגיד עם יש לי Nevada Democratic

אז אני רוצה שהתוכנית תדפיס there is 2 a and 14 letters and 1 space.

כאילו שתבין מידע מהמשפט. לא ממש למדתי מחרוזות אז קשה לי להבין על מה מדובר.

קישור לתוכן
שתף באתרים אחרים

הבנתי בדיוק מה התכוונת.

אתה צריך לולאה שכל פעם תקרא תו בודד ותבדוק:

אם הוא רווח, להגדיל משתנה מסוים ב-1.

אם הוא a, להגדיל משתנה אחר ב-1.

כל מקרה אחר, להגדיל משתנה שלישי ב-1.

ובסוף להדפיס את התוצאות.

הפונקציה scanf דווקא לא מתאימה כאן, כי היא מדלגת על רווחים. אתה צריך להשתמש ב-getchar במקום זה:

int ch = getchar();

ואתה צריך לדאוג שהלולאה תפסיק לקרוא כשאתה מגיע לסוף הקלט (ch == EOF) או לסוף שורה ('ch == '\n).

קישור לתוכן
שתף באתרים אחרים


include <stdio.h>
int main()
{
int a=0,e=0,i=0,o=0,u=0,letters=0,others=0;
char character,sentence;
do
{
sentence=getchar();
sentence=character;
switch(character)
{
case 'a': a++;break;
case 'e': e++;break;
case 'i': i++;break;
case 'o': o++;break;
case 'u': u++;break;
case 'A'-'Z' && 'a'-'z': letters++; break;
default: others++; break;
}
}
while(sentence==EOF);
printf("Numbers of characters:a %d; e %d; i %d; o %d; u %d; letters %d; other %d",&a,&e,&i,&o,&u,&letters,&others);
}

זה התוכנית שהכנתי, אך הרעיון שזה בודק כל תו בודד נראה לי התפספס לי בתרגיל לא ממש הבנתי את הקטע של לבדוק כל תו בודד. האם אתה יכול להסביר לי את זה?

התוכנה נכשלת בגלל בעיה לוגית שהיא:

1) אני לא בטוח שבדקתי כל תו בודד נכון.

2) קשה לי להבדיל בין הcase האחרון לdefault . אםה case לפני הDEFAULT הוא כל האותיות חוץ מa,i,o,u,e אז אני צריך לעשות כל האתיות פחות האותיות ניקוד באנגלית? לא ממש הצלחתי להתעסק עם זה ולבודד את הסימנים והאותות מdefault. בקיצור קשה לי להגדיר את הסימנים בCASE ובכך שDEFAULT היה כל שאר האותיות. האם מותר להשתמש ב|| וב&& בcase?

קישור לתוכן
שתף באתרים אחרים

כמה בעיות:

- מה שאתה עושה כרגע זה לקלוט מהמשתמש תו ל sentence ואז לדרוס אותו עם המשתנה character (שלא אותחל). אין לך צורך במשתנה נוסף (sentence), אתה פשוט קולט תו, בודק אותו וחוזר שוב ושוב על הפעולה הזו. פשוט תעיף את sentence (שאגב מיצג גם תו אחד ולא משפט) ותציב את getchar() ב character.

- בתנאי של הלולאה כתבת sentence==EOF. שני דברים: התכוונת ל sentence != EOF כי אתה רוצה להמשיך לרוץ כל עוד לא הגעת לסוף הקלט. דבר נוסף זה לא יעבוד במצב הזה כי אתה בכל מקרה קולט תו ככה שלא תגיע למצב שב character יהיה EOF. פשוט תקבע תו שיהווה סימן לסיום, כמו למשל התו 0 - while(character != '0').

- ל printf לא שולחים מצביעים כמו ל scanf אז תוריד את כל ה&-ים לפני המשתנים.

- אני לא יודע עם איזה קומפיילר אתה עובד אבל אני לא בטוח שמה שעשית שם ב case ( השורה עם ה'A'-'Z' && 'a'-'z') תקני (לפי התקן של c) אז אני חושב שעדיף להשתמש ב if\else במקום.

קישור לתוכן
שתף באתרים אחרים

לא ממש הבנתי את הקטע עם קליטת התו . אני הרי צריך לקלוט משפט ואז לבדוק תו תו .

אני מחויב להשתמש בתרגיל בswitch case ולסים את הבדיקה ברגע שהמשתמש לוחץ enter אחרי שהקליד. עידכנתי וערכתי את התרגיל לפי הבעיות שהבנתי :


#include <stdio.h>
int main()
{
int a=0,e=0,i=0,o=0,u=0,letters=0,others=0;
char character;
do
{
character=getchar();
switch(character)
{
case 'a': a++;break;
case 'e': e++;break;
case 'i': i++;break;
case 'o': o++;break;
case 'u': u++;break;
case 'A': a++;break;
case 'E': e++;break;
case 'I': i++;break;
case 'O': o++;break;
case 'U': u++;break;
default:
if(((character>' ')&&(character<'@'))||((character>[)&(character<`))||((character>{)&(character<~)))
{
others++;
}
else
{
letters++;
}
break;
}
}
while(character!=EOF);
printf("Numbers of characters:a %d; e %d; i %d; o %d; u %d; letters %d; other %d",a,e,i,o,u,letters,others);
}

בשביל התווים השתמשתי בטבלאת האסקי, אך יש לי בעיית קימפול ->

main.c:22: parse error before `['

main.c:22: parse error before ``'

main.c:22: parse error before `{'

main.c:22: parse error before `)'

===

אני ממש במצב גרוע אני לא מצליח לפצח את זה. :-[

קישור לתוכן
שתף באתרים אחרים

ארכיון

דיון זה הועבר לארכיון ולא ניתן להוסיף בו תגובות חדשות.


×
  • צור חדש...