Skip to content

Commit 4ec6db9

Browse files
committed
Add: Exercise 6-5
1 parent 3a9d5e6 commit 4ec6db9

File tree

7 files changed

+204
-0
lines changed

7 files changed

+204
-0
lines changed

Chapter-6/Exercise 6-5/buffer.c

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
#include <stdio.h>
2+
#include <string.h>
3+
#define BUFSIZE 100
4+
5+
int buf[BUFSIZE]; /* buffer for ungetch */
6+
int bufp = 0; /* buffer pointer (not a real pointer) */
7+
8+
int getch(void) /* get a (possibly pushed back) character */ {
9+
return (bufp > 0) ? buf[--bufp] : getchar();
10+
}
11+
12+
void ungetch(int c) /* push character back on input */ {
13+
if (bufp >= BUFSIZE)
14+
printf("ungetch : too many characters\n");
15+
else
16+
buf[bufp++] = c;
17+
}
18+
19+
void ungets(char s[]) /* push string s back to input */ {
20+
int i = strlen(s);
21+
while (i > 0) ungetch(s[--i]);
22+
}

Chapter-6/Exercise 6-5/buffer.h

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
#ifndef BUFFER_H
2+
#define BUFFER_H
3+
4+
int getch(void);
5+
6+
void ungetch(int);
7+
8+
void ungets(char []);
9+
10+
#endif

Chapter-6/Exercise 6-5/io.c

+51
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
#include <stdio.h>
2+
#include <stdlib.h>
3+
#include <string.h>
4+
#include <ctype.h>
5+
#include "buffer.h"
6+
#include "io.h"
7+
8+
char *_strdup(char *s) { /* make a duplicate of s */
9+
char *p;
10+
11+
p = (char *) malloc(strlen(s) + 1); /* +1 for '\0' */
12+
if (p != NULL)
13+
strcpy(p, s);
14+
return p;
15+
}
16+
17+
/* _strndup: make a duplicate of at most 6 characters of s*/
18+
char *_strndup(char *s, int n) {
19+
char *p;
20+
21+
p = (char *) malloc(n +1);
22+
if (p != NULL)
23+
strncpy(p, s, n);
24+
return p;
25+
}
26+
27+
/* getword: get next word or character from input */
28+
int getword(char *word, int lim) {
29+
int c;
30+
char *w = word;
31+
32+
/* skip the whitespaces */
33+
while (isspace(c = getch()))
34+
;
35+
if (c != EOF)
36+
*w++ = c;
37+
if (!isalpha(c)) {
38+
*w = '\0';
39+
return c;
40+
}
41+
42+
while (--lim) {
43+
if (!isalnum(*w = getch())) {
44+
ungetch(*w);
45+
break;
46+
}
47+
w++;
48+
}
49+
*w = '\0';
50+
return word[0];
51+
}

Chapter-6/Exercise 6-5/io.h

+9
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
#ifndef IO_H
2+
#define IO_H
3+
4+
char *_strdup(char *s);
5+
char *_strndup(char *s, int n);
6+
7+
int getword(char *word, int lim);
8+
9+
#endif

Chapter-6/Exercise 6-5/main.c

+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
#include <stdio.h>
2+
#include "nlist.h"
3+
4+
int main() {
5+
install("satyajit", "ghana");
6+
7+
struct nlist *search;
8+
if ((search = lookup("satyajit")) != NULL)
9+
printf("name : %s, defn : %s\n", search -> name, search -> defn);
10+
/* delete the name */
11+
if (undef("satyajit") == 0 ) {
12+
printf("deleted !");
13+
printf(" lookup : %d\n", lookup("satyajit"));
14+
}
15+
16+
return 0;
17+
}

Chapter-6/Exercise 6-5/nlist.c

+77
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
#include <stdio.h>
2+
#include <stdlib.h>
3+
#include <string.h>
4+
5+
#include "nlist.h"
6+
#include "io.h"
7+
8+
#define HASHSIZE 101
9+
10+
static struct nlist *hashtab[HASHSIZE]; /* pointer table */
11+
12+
/* hash: form hash value for string s */
13+
unsigned hash(char *s) {
14+
unsigned hashval;
15+
16+
for (hashval = 0; *s != '\0' ; s++)
17+
hashval = *s + 31 * hashval;
18+
19+
return hashval % HASHSIZE;
20+
}
21+
22+
/* lookup: look for s in hashtab */
23+
struct nlist *lookup(char *s) {
24+
struct nlist *np;
25+
26+
for (np = hashtab[hash(s)] ; np != NULL ; np = np -> next)
27+
if (strcmp(s, np -> name) == 0)
28+
return np; /* found */
29+
return NULL; /* not found */
30+
}
31+
32+
/* install: put(name, defn) in hashtab */
33+
struct nlist *install(char* name, char* defn) {
34+
struct nlist *np;
35+
unsigned hashval;
36+
37+
if ((np = lookup(name)) == NULL) { /* not found */
38+
np = (struct nlist *) malloc(sizeof(*np));
39+
if (np == NULL || (np -> name = _strdup(name)) == NULL)
40+
return NULL;
41+
hashval = hash(name);
42+
np -> next = hashtab[hashval];
43+
hashtab[hashval] = np;
44+
} else /* that means its already there */
45+
free((void*) np -> defn); /* free previous defn */
46+
if ((np -> defn = _strdup(defn)) == NULL)
47+
return NULL;
48+
return np;
49+
}
50+
51+
/* undef: removes a name from the hashtab */
52+
int undef(char* name) {
53+
struct nlist *np;
54+
55+
if ((np = lookup(name)) == NULL)
56+
return 1; /* the name was not found */
57+
58+
struct nlist *prev_np = NULL;
59+
unsigned hashval = hash(name);
60+
for (np = hashtab[hashval] ; np != NULL; prev_np = np, np = np -> next) {
61+
if (strcmp(np -> name, name) == 0) { /* found the node with that name */
62+
if (prev_np == NULL) /* at the beginning ? */
63+
hashtab[hashval] = np -> next;
64+
else /* somewhere in the middle */
65+
prev_np -> next = np -> next;
66+
/* free the memory */
67+
free(np -> name);
68+
free(np -> defn);
69+
free(np);
70+
71+
return 0;
72+
}
73+
}
74+
75+
return 1; /* name not found */
76+
}
77+

Chapter-6/Exercise 6-5/nlist.h

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
#ifndef NLIST_H
2+
#define NLIST_H
3+
4+
struct nlist { /* table entry */
5+
struct nlist *next; /* next entry in the chain */
6+
char *name; /* defined name */
7+
char *defn; /* replacement text */
8+
};
9+
10+
unsigned hash(char*);
11+
12+
struct nlist *lookup(char*);
13+
14+
struct nlist *install(char*, char*);
15+
16+
int undef(char*);
17+
18+
#endif

0 commit comments

Comments
 (0)