casting למערך בC

PINGPONG11

New member
casting למערך בC

היי. אם הגדרתי מערך של מצביעים לInt
ואני רוצה לעשות קאסטינג לכל המערך כך שיהיה מערך של מצביעים לdouble
האם נכון לכתוב כך?

typedef int* p_int;
typedef double* p_double;

p_int* arr;
int i;

for(i=0;i<MAX;i++)
(p_double)arr;
(p_double*)arr;


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

השורה:

for(i=0;i<MAX;i++)
(p_double)arr;

רצה על כל אברי המערך, מכל אחד מהם מייצרת מצביע זמני מטיפוס של מצביע-ל-double, ואז זורקת את המצביע הזמני לפח ולא עושה איתו כלום.

השורה:

(p_double*)arr;

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

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

p_double temp = (p_double)arr;

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

cast הוא דרך "להשתיק" את הקומפיילר - להגיד לו: "אני יודע הרבה יותר טוב ממך מה אני עושה, תן לי גישה ישירה לזיכרון ואני כבר אדאג לטפל בהכל". היות ובמקרה שלך בכלל לא נראה שאתה באמת מבין יותר טוב מהקומפיילר מה אתה עושה, אני מציע שתסביר לנו מה בכלל ניסית לעשות ומה המטרה שלך, ואז אולי אפשר יהיה לכוון אותך יותר טוב.
 

PINGPONG11

New member
תודה על ההסבר המפורט!

יש לי קוד של ADT כללי. אחת הפונקציות בקוד הזה היא:


typedef void* p_gen;

p_gen* Arr(DB db);

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

אני רוצה להשתמש במבנה הזה כדי להחזיק structים כאשר אחד מהשדות של הstruct הוא int num, ואני רוצה לממש פונקציה שתגדיל כל num ב-1.
אז בעצם מה שאני אעשה זה ליצור מערך עם כל המצביעים לstructים ואז להגדיל כל num ב1:

typedef struct MEN* PMEN;
...
p_gen* arr1=Arr(db);
int i;
for(i=0;i<MAX;i++)
arr1->num++;


אבל אם אני לא אעשה קאסטינג של המצביעים להיות מצביעים לMEN אז אני לא אוכל לגשת לשדה num

מקווה שההסבר ברור..
 
ממש לא ברור ואין לי זמן כרגע להתעמק בזה אז אני אגיד רק שאין שום קשר בין מה ששאלת כאן לבין מה ששאלת בראש השרשור. שם ניסית להפוך מערך של int-ים למערך של double-ים בצורה עקומה להחריד. פה אתה רוצה רק להחזיר מצביע לצורה ה"אמיתית" שלו אחרי שהוא הפך ל *void באדיבות ה ADT. אלו שתי פעולות לגמרי ולחלוטין שונות, השניה היא משהו מקובל והגיוני בתכנות ב C והראשונה זה קשקוש שיסתיים בזבל במשתנים במקרה הטוב ובתעופה של התוכנית במקרה הרע.

אתה הרבה הרבה הרבה יותר מדי מסתבך עם זה. תשב עם עצמך טוב-טוב ותגדיר את כל טיפוסי ה struct-ים שלך, ואחר כך תכניס לעצמך חזק לראש שיש רק שני cast-ים שמותר לך לעשות: אחד, המרה ממצביע ל struct שלך ל *void, והשני המרה בכיוון ההפוך.

תעשה תוכנית פשוטה שרצה על המערך שלך ומקדמת int-ים או עושה מה שבא לה בלי cast של מצביעים. אחר כך תלך צעד קטנטן קדימה ותראה את אתה מכניס את ה struct שלך ל ADT. אחר כך תראה איך אתה מוציא אותו מה ADT. הדרך שאתה עושה כרגע זה לעשות מהכל סלט עגבניות.
 
למעלה