我正在开发一个基本的unix shell,我想添加的一个功能是'history'命令,该命令会吐出用户在该会话期间尝试过的所有命令。我的研究表明,实现这一点的最佳方法是使用链接列表。
这是我的实现,无论我输入什么命令,它只存储“history”命令。我只在主shell程序中包含了我认为必要的内容。
这是输出
//output
mish> echo Hello World
Hello World
mish> date
Sat Dec 14 16:35:31 EST 2013
mish> history
============ Command History ============
[1] history
[2] history
[3] history
=========================================
mish>
这是主要的shell
//main.c
List *historyList = malloc (sizeof(List));
//get command
addHistory(historyList, command);
//do other shell stuff (parsing, etc.)
if (userInput is "history)
printHistory;
这是history.c
//history.c
typedef struct History{
char *command;
struct History *next;
}History;
typedef struct List{
unsigned int count;
History *top;
}List;
void addHistory(List *list, char *cmd){
History *h = (History*) malloc(sizeof(History));
h->command = cmd;
if (isHistoryEmpty(list)){
h->next = NULL;
list->top = h;
}
else{
h->next = list->top;
list->top = h;
}
list->count++;
}
bool isHistoryEmpty(List *list){
if (list->count == 0){
return true;
}
return false;
}
void clearHistory(List *list){
while (!isHistoryEmpty(list)){
History *temp = list->top;
list->count--;
list->top = list->top->next;
free(temp);
}
free(list);
}
void printHistory(List *list){
int i = 1;
printf("Command History\n");
while (!list->top == NULL){ //this line causes a warning on compilation (comparison between pointer and integer)
History *temp = list->top;
printf("[%d] %s \n", i, temp->command);
list->top = list->top->next;
i++;
}
} 19,2-5 Top
答案 0 :(得分:2)
您不会复制command
,因此所有历史记录项都共享command
缓冲区。当用户键入命令时,它将被读入唯一的缓冲区,并且所有历史记录项都“更改”为最新的命令。
History *h = (History*) malloc(sizeof(History));
h->command = (char*) malloc(sizeof(char) * (strlen(cmd) + 1));
strcpy(h->command, cmd);
清除列表时必须释放副本。
更多错误:
!
的优先级高于==
,因此请使用!=
或使用括号:!(list->top == NULL)
在遍历列表时,您不得修改list->top
。相反,将temp
的声明和初始化移到循环外部,然后使用temp
而不是list->top
。