פורסם 2007 באוקטובר 118 שנים כמו שאמרתי, כשאתה כותב פונקציה כזו הקוד יתקמפל וירוץ, אבל לא יעבוד כראוי.במקרה הטוב התכנית תעיף שגיאה שתגרום לתכנית לקרוס מיד, במקרה הרע התכנית לא תקרוס אלא תהיה דריכת זכרון, מה שיגרום לתקלות רציניות בתכנית או לחילופין לפרצות אבטחה.איזה קוד אתה מתכוון שרץ לך? (תעלה אותו כאן)
פורסם 2007 באוקטובר 118 שנים מחבר בא לך לקרוא 1100 שורות קוד?אני יעלה את המרכזיeat(board,&xIndex,&yIndex,&x,&y,strshr((turn=='w' ? 'w' : 'b'),".k"),"rd",&bWin,&wWin);int eat(Soldier board[][10],int* xIndex,int* yIndex,int* x,int* y,char* turn,char* direction,int* bWin,int* wWin){ makeAmove(board,xIndex,yIndex,x,y,turn,direction); printf(" "); makeAmove(board,xIndex,yIndex,x,y,turn,direction); turn[0]=='w' ? --(*bWin) : --(*wWin);}char* strshr(char c, char* str){ char* string; int i; string[0]=c; for(i=1;i<=strlen(str);++i) string[i]=str[i-1]; string[i+1]='\0'; return(string);}int makeAmove(Soldier board[][10], int* xI, int* yI, int* x , int* y, char* turn, char* move){ strcpy(board[*yI][*xI].kind,"empty"); gotoxy(*x-1,*y); printf(" "); if(move[0]=='l') { --(*xI); *x-=4; } else { ++(*xI); *x+=4; } if(move[1]=='u') { --(*yI); *y-=2; } else { ++(*yI); *y+=2; } gotoxy(*x,*y); if(turn[2]=='k' || (*yI==1 && turn[0]=='b') || (*yI==8 && turn[0]=='w')) { printf(".K"); gotoxy(*x-1,*y); strcpy(&(board[*yI][*xI].kind[1]),".k"); } if(turn[0]=='w') { printf("W"); board[*yI][*xI].kind[0]='w'; } else { printf("B"); board[*yI][*xI].kind[0]='b'; } gotoxy((*x)-1,*y); return(1);}
פורסם 2007 באוקטובר 118 שנים כשאתה מגדיר משתנה בלי לשים בו ערך, אז הוא פשוט מקבל את הערך שהיה שם קודם בזכרון. בסיכוי כלשהו, הערך הזה תקין, כלומר הוא מצביע לאיזשהו מקום חוקי בזכרון (במיוחד אם קראת לפני כן לפונקציה אחרת שהשתמשה במצביעים).אותו מקום יכול להיות מקום שהוקצה על ידי התכנית שלך ומשמש למטרה אחרת, מה שיגרום למידע שישב שם להתלכלך. אם אותו מידע לא היה בשימוש, אז זה לא משנה. יכול להיות שזה מקום שהוקצה וכבר שוחרר, אבל כיוון שלא הוקצה מקום חדש מאז, המקום הזה עדיין "פנוי", ולכן דריכה עליו לא יכולה להזיק. ההנחה שלי היא שזה בדיוק מה שקרה במקרה שלך.אם אותו מידע כן היה בשימוש, אז זה יגרום לשיבוש בהמשך מהלך התכנית.
פורסם 2007 באוקטובר 118 שנים מחבר אז תמיד הדרך היחידה להחזיר מחרוזת היאא. שהפונקציה תקצה את המערך.ב. שהפונקציה תקבל פרמטר נוסף מטיפוס *char, שמצביע למערך שכבר הוקצה מראש.לא משנה כלום?
פורסם 2007 באוקטובר 218 שנים כמו שאמרתי, אתה יכול גם לקבל מחרוזת שהוקצתה מראש (כל הפונקציה ב-string.h עובדות ככה).המחרוזת הזו יכולה להיות מוקצית סטטית או דינמית.אם אתה רוצה שהפונקציה תקצה את המחרוזת בעצמה, ההקצאה חייבת להיות דינמית.לדוגמה, אתה יכול לעשות ככה:void strshr(char c, char* str, char* dst){ int i; dst[0]=c; for(i=1;i<=strlen(str);++i) dst[i]=str[i-1]; dst[i+1]='\0';}ואז לקרוא לפונקציה ככה (הקצאה סטטית):char dst[10];strshr(c, str, dst);או לחילופין (הקצאה דינמית):char* dst = (char*)malloc(10);strshr(c, str, dst);היתרון של פונקציה שמקצה בעצמה את המקום למחרוזת הוא שככה הפונקציה יודעת בדיוק כמה מקום היא צריכה להקצות.היתרון של פונקציה שמקבלת מצביע למחרוזת שהוקצתה מראש הוא שזה מאפשר לך יותר גמישות (אתה יכול להעביר מערך שכבר הקצית בעבר, וככה "למחזר" מערכים ולחסוך הקצאות מיותרות) וככה אתה דואג שהפונקציה שמקצה את המערך היא זו שמשחררת אותו (סיכוי יותר קטן שתשכח לשחרר את המערך).
פורסם 2007 באוקטובר 218 שנים לדוגמה, אתה יכול לעשות ככה:void strshr(char c, char* str, char* dst){ int i; dst[0]=c; for(i=1;i<=strlen(str);++i) dst[i]=str[i-1]; dst[i+1]='\0';*********}כשהלולאה תסתיים i כבר יהיה שווה strlen(str) + 1 לא? כך שלהציב ב dst[i+1] יהיה שגיאה..
ארכיון
דיון זה הועבר לארכיון ולא ניתן להוסיף בו תגובות חדשות.