前两天曾经贴过一个帖子(http://expert.csdn.net/Expert/TopicView1.asp?id=2026605),可是回应的人很少,我觉得这是一个很应该讨论以下的问题:
直接用malloc创建数组:我这样测试过:
int *a;
a = malloc(4*sizeof(int));
a[0] = 0;a[1] = 1;a[2] = 2; a[3] = 3;
这样创建的数组a行为正常,没有什么问题可是请看这段代码:
这是定义
typedef struct
{
int nMath, nEng, nComp;
char *szNum, *szName;
} STUDENTRECORD, *PSTUDENTRECORD;/* The node type of the record struct list */
typedef struct tagSTUDENTRECORDLIST
{
STUDENTRECORD sr;
struct tagSTUDENTRECORDLIST *pNext;
} STUDENTRECORDLIST, *PSTUDENTRECORDLIST;BOOL SRList_CopyToArray(const PSTUDENTRECORDLIST srlistHead, const PSTUDENTRECORDLIST srlistTail, PSTUDENTRECORD *pasr, int cList){
int i = 0;
PSTUDENTRECORDLIST srlistTemp = srlistHead;
*pasr = alloc(cList * sizeof(STUDENTRECORD));
if (!*pasr) return TRUE; /* Memory not enough */ while (srlistTemp)
{
(*pasr)[i] = srlistTemp->sr;
i++;
srlistTemp = srlistTemp->pNext;
}; for (i = 0; i < cList; i++)
printf("%s\n", ((*pasr)[i]).szNum); return FALSE;
}
其中pasr是指向STUDENTRECORD数组的指针,为什么这段程序运行时会有内存访问违规?
而且更奇怪的是,创建的数组在(*pasr)[1]到(*pasr)[4]是正常的数据,但是对(*pasr)[0]的访问会导致内存访问违规,在tc和vc下有一样的结果(当然tc不会有内存保护,打印(*pasr)[0]的内容是乱码)
请大家讨论一下这种情况,难道编译器在处理数组时还有什么特殊手段?另外,编译器如何知道一个数组的大小?会不会在数组结尾有\0?或者像Pascal中那样在字符串的第一个字节保存数组的长度?

解决方案 »

  1.   

    你的问题我上次好像回答过malloc返回值的类型一定要加以限制,不能像a = malloc(4*sizeof(int));这样必须这样:a = (int *)malloc(4*sizeof(int));
      

  2.   

    如果你不用类型加以限制,malloc就会出错
    也就是说,对于我们来说malloc不单是分配空间,而且分配的时候是有类型的*pasr = alloc(cList * sizeof(STUDENTRECORD));    //原来的代码pasr = (PSTUDENTRECORD *)alloc(cList * sizeof(STUDENTRECORD)); //现在的代码
      

  3.   


    *pasr = malloc(cList * sizeof(STUDENTRECORD));
    这里会报错,malloc分配返回的是 void指针,这点没说头。
    你要用某种指针去引用的话,就应该转换类型。
    所以应该是
    *pasr = (PSTUDENTRECORD *)alloc(cList * sizeof(STUDENTRECORD)); 
    才对。
    另,把你的调用代码贴出来。我试试,我想应该不会有这种问题的。
    内存违规通常都是超界了,
    这一句我没读懂,(*pasr)[i] = srlistTemp->sr;
    (*pasr)[i] 应该是一个STUDENTRECORD结构,怎么你会这样赋值!
      

  4.   

    hujun614(Softworm) :
    (*pasr)[i] 是一个STUDENTRECORD结构,srlistTemp是PSTUDENTRECORDLIST结构
    而PSTUDENTRECORDLIST结构中的sr字段是STUDENTRECORD类型,所以可以这样负值呀!SeainBlue(爱海) :我去试试
      

  5.   

    不过SeainBlue你说得也不对,malloc就是可以那样用,编译器会自动转换指针的类型