-5
這是一個括號平衡代碼。我提交併得到了我的教授的評論。用C語言平衡的括號
「您的堆棧應該動態增長和縮小以適應任意數量的字符。不要使用scanf for%s,這是有風險的行爲,並且Adams博士不會批准。編寫幫助函數以讀取字符新隊。」
你能幫我解決這個問題嗎?
這是一個括號平衡代碼。我提交併得到了我的教授的評論。用C語言平衡的括號
「您的堆棧應該動態增長和縮小以適應任意數量的字符。不要使用scanf for%s,這是有風險的行爲,並且Adams博士不會批准。編寫幫助函數以讀取字符新隊。」
你能幫我解決這個問題嗎?
你的教授是正確的,他給你的解決方案:不要讀一行到scanf("%s",...)
緩衝區:任意長的一行將導致緩衝區溢出。您不需要閱讀完整行,只需讓check_balanced
一次讀取一個字符:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "stack.h"
#define TRUE 1
#define FALSE 0
int check_matching(void);
int main(int argc, char *argv[]) {
int n, i, c;
/* get the number of cases */
if (scanf("%d", &n) != 1) {
printf("invalid number\n");
exit(1);
}
/* consume the rest of the line */
while ((c = getchar()) != EOF && c != '\n')
continue;
for (i = 0; i < n; i++) {
if (check_matching()) {
printf("yes\n");
} else {
printf("no\n");
}
}
return 0;
}
int check_matching(void) {
int ret = TRUE, symbol, checkSymbol;
LinkedStack *pStack;
StackNode *pNode;
StackNode node;
pStack = createLinkedStack();
if (pStack == NULL) {
printf("createLinkedStack failed\n");
exit(1);
}
/* read a full line, one byte at a time */
while ((symbol = getchar()) != EOF && symbol != '\n') {
if (ret == FALSE)
continue;
switch (symbol) {
case '(':
case '[':
case '{':
node.data = symbol;
pushLS(pStack, node);
break;
case ')':
case ']':
case '}':
pNode = popLS(pStack);
if (pNode == NULL) {
ret = FALSE;
break;
} else {
checkSymbol = pNode->data;
if ((symbol == ')' && checkSymbol == '(')
|| (symbol == ']' && checkSymbol == '[')
|| (symbol == '}' && checkSymbol == '{')) {
// Right case. do nothing.
} else {
ret = FALSE;
}
free(pNode);
}
break;
}
}
if (isLinkedStackEmpty(pStack) == FALSE) {
ret = FALSE;
}
deleteLinkedStack(pStack);
return ret;
}
非常感謝你! –
您的TA是100%正確的。你不安全地讀入一個字節大小的存儲區。既不使用%s,也不計入將要添加的尾隨NULL,也不會計入超過一個字符的輸入。您可以按照您的技術支持建議並創建一個帶有循環的幫助函數,該函數一次讀取一個字符,並將其添加到動態大小的數組中,直到遇到換行符爲止。 –
爲了完整,請發佈堆棧實現。 – chqrlie