使用sscanf(),将字符串读取到int数组?

时间:2009-09-27 10:51:14

标签: algorithm arrays numbers scanf

我有这个字符串:

12 4 the quick 99 -1 fox dog \

我想要的程序:

myArray[] = {12, 4, 99, -1};

我如何进行多号扫描?

1 个答案:

答案 0 :(得分:1)

请参阅我对您的其他问题here的回答。替换strtok部分以识别非数字单词并且既不增加计数(在第一遍中)也不将它们加载到数组中(在第二遍中),这是一个相对简单的事情。

代码更改如下:

使用输入文件:

12 3 45 6 7 8
3 5 6 7
7 0 -1 4 5
12 4 the quick 99 -1 fox dog \

它产生的输出如下:

0x8e42170, size = 6:
   12 3 45 6 7 8
0x8e421d0, size = 4:
   3 5 6 7
0x8e421e0, size = 5:
   7 0 -1 4 5
0x8e42278, size = 4:
   12 4 99 -1

以下是产生该输出的代码:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>

// This is the linked list of integer arrays.

typedef struct _tIntArray {
    int size;
    int *array;
    struct _tIntArray *next;
} tIntArray;
static tIntArray *first = NULL;
static tIntArray *last = NULL;

// Check that argument is numeric, optional minus sign followed by
// zero or more digits (you may want one or more).

static int isAllNumeric (char *word) {
    char *s = word;
    if (*s == '-')
        s++;
    for (; *s != '\0'; s++)
        if ((*s < '0') || (*s > '9'))
            return 0;
    return 1;
}

// Add a line of integers as a node.

static int addNode (char *str) {
    tIntArray *curr;  // pointers for new integer array.
    char *word;       // word within string.
    char *tmpStr;     // temp copy of buffer.
    int fldCnt;       // field count for line.
    int i;

    // Count number of fields.

    if ((tmpStr = strdup (str)) == NULL) {
        printf ("Cannot allocate duplicate string (%d).\n", errno);
        return 1;
    }
    fldCnt = 0;
    for (word = strtok (tmpStr, " "); word; word = strtok (NULL, " "))
        if (isAllNumeric (word))
            fldCnt++;
    free (tmpStr);

    // Create new linked list node.

    if ((curr = malloc (sizeof (tIntArray))) == NULL) {
        printf ("Cannot allocate integer array node (%d).\n", errno);
        return 1;
    }

    curr->size = fldCnt;
    if ((curr->array = malloc (fldCnt * sizeof (int))) == NULL) {
        printf ("Cannot allocate integer array (%d).\n", errno);
        free (curr);
        return 1;
    }
    curr->next = NULL;

    for (i = 0, word = strtok (str, " "); word; word = strtok (NULL, " "))
        if (isAllNumeric (word))
            curr->array[i++] = atoi (word);

    if (last == NULL)
        first = last = curr;
    else {
        last->next = curr;
        last = curr;
    }

    return 0;
}

int main(void) {
    int lineSz;       // current line size.
    char *buff;       // buffer to hold line.
    FILE *fin;        // input file handle.
    long offset;      // offset for re-allocating line buffer.
    tIntArray *curr;  // pointers for new integer array.
    int i;

    // Open file.

    if ((fin = fopen ("qq.in", "r")) == NULL) {
        printf ("Cannot open qq.in, errno = %d\n", errno);
        return 1;
    }

    // Allocate initial line.

    lineSz = 2;
    if ((buff = malloc (lineSz+1)) == NULL) {
        printf ("Cannot allocate initial memory, errno = %d.\n", errno);
        return 1;
    }

    // Loop forever.

    while (1) {
        // Save offset in case we need to re-read.

        offset = ftell (fin);

        // Get line, exit if end of file.

        if (fgets (buff, lineSz, fin) == NULL)
            break;

        // If no newline, assume buffer wasn't big enough.

        if (buff[strlen(buff)-1] != '\n') {
            // Get bigger buffer and seek back to line start and retry.

            free (buff);
            lineSz += 3;
            if ((buff = malloc (lineSz+1)) == NULL) {
                printf ("Cannot allocate extra memory, errno = %d.\n", errno);
                return 1;
            }
            if (fseek (fin, offset, SEEK_SET) != 0) {
                printf ("Cannot seek, errno = %d.\n", errno);
                return 1;
            }
            continue;
        }

        // Remove newline and process.

        buff[strlen(buff)-1] = '\0';
        if (addNode (buff) != 0)
            return 1;
    }

    // Dump table for debugging.

    for (curr = first; curr != NULL; curr = curr->next) {
        printf ("%p, size = %d:\n  ", curr, curr->size);
        for (i = 0; i < curr->size; i++)
            printf (" %d", curr->array[i]);
        printf ("\n");
    }

    // Free resources and exit.

    free (buff);
    fclose (fin);
    return 0;
}