|
|
1.1 root 1: #include <sys/types.h>
2: #ifndef BSD4_2
3: #include <ndir.h>
4: #else
5: #include <sys/dir.h>
6: #endif
7:
8: /*
9: * char *spname(name, score)
10: * char name[];
11: * int *score;
12: *
13: * returns pointer to correctly spelled name,
14: * or 0 if no reasonable name is found;
15: * uses a static buffer to store correct name,
16: * so copy it if you want to call the routine again.
17: * score records how good the match was; ignore if NULL return.
18: */
19: char *
20: spname(name, score)
21: register char *name;
22: int *score;
23: {
24: #undef DIRSIZ
25: #define DIRSIZ 14
26: register char *p, *q, *new;
27: register d, nd;
28: register DIR *dirf;
29: register struct direct *ep;
30: static char newname[128], guess[DIRSIZ+1], best[DIRSIZ+1];
31:
32: new = newname;
33: *score = 0;
34: for(;;){
35: if (new >= &newname[128-DIRSIZ-2])
36: return((char *)0);
37: while(*name == '/')
38: *new++ = *name++;
39: *new = '\0';
40: if(*name == '\0')
41: return(newname);
42: p = guess;
43: while(*name!='/' && *name!='\0'){
44: if(p != guess+DIRSIZ)
45: *p++ = *name;
46: name++;
47: }
48: *p = '\0';
49: if((dirf=opendir(*newname? newname : ".",0)) == NULL)
50: return((char *)0);
51: d = 3;
52: while(ep = readdir(dirf)) {
53: nd = SPdist(ep->d_name, guess);
54: if (nd>0
55: && (SPeq(".", ep->d_name) || SPeq("..", ep->d_name)))
56: continue;
57: if(nd<d) {
58: p = best;
59: q = ep->d_name;
60: do; while(*p++ = *q++);
61: d = nd;
62: if(d == 0)
63: break;
64: }
65: }
66: closedir(dirf);
67: if(d == 3)
68: return((char *)0);
69: p = best;
70: *score += d;
71: do; while(*new++ = *p++);
72: --new;
73: }
74: }
75: /*
76: * very rough spelling metric
77: * 0 if the strings are identical
78: * 1 if two chars are interchanged
79: * 2 if one char wrong, added or deleted
80: * 3 otherwise
81: */
82: SPdist(s, t)
83: register char *s, *t;
84: {
85: while(*s++ == *t)
86: if(*t++ == '\0')
87: return(0);
88: if(*--s){
89: if(*t){
90: if(s[1] && t[1] && *s==t[1] && *t==s[1] && SPeq(s+2,t+2))
91: return(1);
92: if(SPeq(s+1, t+1))
93: return(2);
94: }
95: if(SPeq(s+1, t))
96: return(2);
97: }
98: if(*t && SPeq(s, t+1))
99: return(2);
100: return(3);
101: }
102: SPeq(s, t)
103: register char *s, *t;
104: {
105: while(*s++ == *t)
106: if(*t++ == '\0')
107: return(1);
108: return(0);
109: }
110:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.