📄 doscan.c
字号:
/* doscan.c - doscan */
/* Character look-ahead to be implemented as: ch=control(unit,TCNEXTC) */
#include <ctype.h>
#define EOF (-1)
#define NULL 0
#define SPC 01
#define STP 02
#define SHORT 0
#define REGULAR 1
#define LONG 2
char *_getccl();
char _sctab[128] = {
0,0,0,0,0,0,0,0,
0,SPC,SPC,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
SPC,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,
};
/*------------------------------------------------------------------------
* _doscan -- scan and recognize input according to a format
*------------------------------------------------------------------------
*/
_doscan(fmt, argp, getch, ungetch, arg1, arg2 )
register char *fmt; /* Format string for the scanf */
register int **argp; /* Arguments to scanf */
int (*getch)(); /* Function to get a character */
int (*ungetch)(); /* Function to unget a character*/
int arg1; /* 1st argument to getch/ungetch*/
int arg2; /* 2nd argument to getch/ungetch*/
{
register int ch;
int nmatch, len, ch1;
int **ptr, fileended, size;
nmatch = 0;
fileended = 0;
for (;;) switch (ch = *fmt++) {
case '\0':
return (nmatch);
case '%':
if ((ch = *fmt++) == '%')
goto def;
ptr = 0;
if (ch != '*')
ptr = argp++;
else
ch = *fmt++;
len = 0;
size = REGULAR;
while (isdigit(ch)) {
len = len*10 + ch - '0';
ch = *fmt++;
}
if (len == 0)
len = 30000;
if (ch=='l') {
ch = *fmt++;
size = LONG;
} else if (ch=='h') {
size = SHORT;
ch = *fmt++;
} else if (ch=='[')
fmt = _getccl(fmt);
if (isupper(ch)) {
ch = tolower(ch);
size = LONG;
}
if (ch == '\0')
return(-1);
if (_innum(ptr, ch, len, size, getch, ungetch,
arg1, arg2, &fileended) && ptr)
nmatch++;
if (fileended)
return(nmatch? nmatch: -1);
break;
case ' ':
case '\n':
case '\t':
while ((ch1 = (*getch)(arg1, arg2))==' ' || ch1=='\t' || ch1=='\n')
;
if (ch1 != EOF)
(*ungetch)(arg1, arg2);
break;
default:
def:
ch1 = (*getch)(arg1, arg2);
if (ch1 != ch) {
if (ch1==EOF)
return(-1);
(*ungetch)(arg1, arg2);
return(nmatch);
}
}
}
_innum(ptr, type, len, size, getch, ungetch, arg1, arg2, eofptr)
int **ptr;
int type;
int len;
int size;
int (*getch)();
int (*ungetch)();
int arg1;
int arg2;
int *eofptr;
{
extern double atof();
register char *np;
char numbuf[64];
register c, base;
int expseen, negflg, c1, ndigit;
long lcval;
if (type=='c' || type=='s' || type=='[')
return(_instr(ptr? *(char **)ptr: (char *)NULL, type,
len, getch, ungetch, arg1, arg2, eofptr));
lcval = 0;
ndigit = 0;
base = 10;
if (type=='o')
base = 8;
else if (type=='x')
base = 16;
np = numbuf;
expseen = 0;
negflg = 0;
while ((c = (*getch)(arg1, arg2))==' ' || c=='\t' || c=='\n');
if (c=='-') {
negflg++;
*np++ = c;
c = (*getch)(arg1, arg2);
len--;
} else if (c=='+') {
len--;
c = (*getch)(arg1, arg2);
}
for ( ; --len>=0; *np++ = c, c = (*getch)(arg1, arg2)) {
if (isdigit(c)
|| base==16 && ('a'<=c && c<='f' || 'A'<=c && c<='F')) {
ndigit++;
if (base==8)
lcval <<=3;
else if (base==10)
lcval = ((lcval<<2) + lcval)<<1;
else
lcval <<= 4;
c1 = c;
if ('0'<=c && c<='9')
c -= '0';
else if ('a'<=c && c<='f')
c -= 'a'-10;
else
c -= 'A'-10;
lcval += c;
c = c1;
continue;
} else
break;
}
if (negflg)
lcval = -lcval;
if (c != EOF) {
(*ungetch)(arg1, arg2);
*eofptr = 0;
} else
*eofptr = 1;
if (ptr==NULL || np==numbuf)
return(0);
*np++ = 0;
switch(size) {
case SHORT:
**(short **)ptr = lcval;
break;
case REGULAR:
**(int **)ptr = lcval;
break;
case LONG:
**(long **)ptr = lcval;
break;
}
return(1);
}
_instr(ptr, type, len, getch, ungetch, arg1, arg2, eofptr)
register char *ptr;
int type;
int len;
int (*getch)();
int (*ungetch)();
int arg1;
int arg2;
int *eofptr;
{
register ch;
register char *optr;
int ignstp;
*eofptr = 0;
optr = ptr;
if (type=='c' && len==30000)
len = 1;
ignstp = 0;
if (type=='s')
ignstp = SPC;
while (_sctab[ch = (*getch)(arg1, arg2)] & ignstp)
if (ch==EOF)
break;
ignstp = SPC;
if (type=='c')
ignstp = 0;
else if (type=='[')
ignstp = STP;
while (ch!=EOF && (_sctab[ch]&ignstp)==0) {
if (ptr)
*ptr++ = ch;
if (--len <= 0)
break;
ch = (*getch)(arg1, arg2);
}
if (ch != EOF) {
if (len > 0)
(*ungetch)(arg1, arg2);
*eofptr = 0;
} else
*eofptr = 1;
if (ptr && ptr!=optr) {
if (type!='c')
*ptr++ = '\0';
return(1);
}
return(0);
}
char *
_getccl(s)
register char *s;
{
register c, t;
t = 0;
if (*s == '^') {
t++;
s++;
}
for (c = 0; c < 128; c++)
if (t)
_sctab[c] &= ~STP;
else
_sctab[c] |= STP;
while (((c = *s++)&0177) != ']') {
if (t)
_sctab[c++] |= STP;
else
_sctab[c++] &= ~STP;
if (c==0)
return(--s);
}
return(s);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -