我有一系列结构,每个结构都描述了我所谓的信号。我用这种方式声明了我的结构:
/* Structure for keywords */
struct varStruct
{
char* varName;
int varOccurence;
} signals[MAX_SIGNALS];
我正在循环中分析文件并动态查找信号声明,在我的情况下称为 newArrayName 。我想做的是,只有在尚未包含的情况下才将读取信号添加到阵列中。否则,我应该增加varOccurence变量。
这是我的代码,但我有分段错误(所以没有进一步的信息)......
// We are in the loop that get the signals sequentially
char* newArrayName = TheValueOfTheReadSignal.
int i;
// We browse all the array...
for(i=0; i < MAX_SIGNALS; i++)
{
// If a signal already has the name of the currently-read signal, we inc its occurence
if(strcmp(signals[i].varName, newArrayName) == 0)
{
signals[i].varOccurence++;
}
// Otherwise, we add a new signal with the read-name and an occurence corresponding to the value of a static variable that's incremented after each signal-reading.
else
{
signals[index_Array].varName = newArrayName;
signals[index_Array].varOccurence = index_Array;
}
}
// We increment index_Array, which is a static int variable
index_Array ++;
// End of the loop that gets the signals
导致分段错误。我的C语言不是很好,我甚至会说我很擅长。我的猜测是信号数组尚未初始化,因此signal [i]对他没有任何意义,但我不知道如何初始化一个结构数组。也许这是另一个原因,我不知道。
非常感谢你的帮助。
答案 0 :(得分:2)
问题是,在第一次迭代时,所有varName
成员都将是NULL
或未初始化的指针(取决于声明signals
的位置)。确保它们已初始化为NULL
:
struct varStruct
{
char* varName;
int varOccurence;
} signals[MAX_SIGNALS] = { {0} };
在传递给NULL
之前检查它是否为strcmp()
:
if(signals[i].varName && strcmp(signals[i].varName, newArrayName) == 0)
如果varName
为NULL,则表示没有填充其他元素,您可以填充它并从循环中断开。
另外确保:
varName
的值是动态分配的(例如,使用malloc()
)并且需要很长时间才能生效,记住free()
varName
时不再必需的。index_Array
元素之前,MAX_SIGNALS
小于signals
。答案 1 :(得分:2)
您正在搜索循环中创建一个“新”条目。这几乎每次都会立即创建一个新的条目。您应该仅在所有现有条目不匹配后创建新条目;即你完成循环后。
你不应该循环到MAX_SIGNALS
,因为在开始时,你的大部分数组都是空的。只有第一个index_Array
元素是真实的。这也会让你用NULL指针初始化你的结构并检查它们,因为你无论如何也不会遍历未初始化的条目。
你盲目地递增index_Array
。只有在确实添加条目时才会递增。
一些变化:
// We are in the loop that get the signals sequentially
char* newArrayName = TheValueOfTheReadSignal.
int found_entry;
found_entry = FALSE; /* A flag that remembers if the entry has been found. */
for(i=0; i < index_Array; i++)
{
if(strcmp(signals[i].varName, newArrayName) == 0)
{
signals[i].varOccurence++;
found_entry = TRUE;
break;
}
}
if (!found_entry)
{
signals[index_Array].varName = newArrayName;
signals[index_Array].varOccurence = index_Array++;
}
答案 2 :(得分:1)
虽然您没有记录signals
中的条目,或者当i
大于记录条目数减去1时,strcmp(signals[i].varName, newArrayName)
会尝试取消引用该无效条目(未初始化或{ {1}})指针NULL
。
除此之外,只要signals[i].varName
变得与index_Array
(或更大)一样大,
MAX_SIGNALS
你写过数组的末尾,这是未定义的行为,可能会直接导致内存损坏和/或分段错误,或者是内存损坏的结果。
在循环中,每次找到具有不同名称的信号时都会写入// We browse all the array...
for(i=0; i < MAX_SIGNALS; i++)
{
// If a signal already has the name of the currently-read signal, we inc its occurence
if(strcmp(signals[i].varName, newArrayName) == 0)
{
signals[i].varOccurence++;
}
// Otherwise, we add a new signal with the read-name and an occurence corresponding to the value of a static variable that's incremented after each signal-reading.
else
{
signals[index_Array].varName = newArrayName;
signals[index_Array].varOccurence = index_Array;
}
}
// We increment index_Array, which is a static int variable
index_Array ++;
,并且每次在循环运行后递增signals[index_Array]
,无论您是否已经有某些信号有这个名字与否。你应该检查你是否已经记录了信号,并且只有在没有写新条目并且增加index_Array
的情况下:
index_Array