Почему я получаю эту пустую строку при печати в C? - PullRequest
2 голосов
/ 16 февраля 2012

Я просто размечаю предложение и кладу его в стек, а затем вытаскиваю обратно каждый токен и распечатываю содержимое.Все работает так, как должно, за исключением того, что я получаю пустую строку после печати первого токена.Кажется, это происходит только тогда, когда я печатаю %s, если я использую что-либо еще, информация является мусором, но я не получаю пустую строку.Я уже попробовал небольшую функцию, чтобы убрать символ новой строки, который захватывает.Любая помощь приветствуется.

#define BUFFER_SIZE 100
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

// self-referential structure
struct stackNode
{   
   char *cData;
   struct stackNode *pNext;
};

typedef struct stackNode StackNode;
typedef StackNode *StackNodePtr;

// function prototypes
void push( StackNodePtr *pTop, char *cInfo );
char* pop( StackNodePtr *pTop );
int isEmpty( StackNodePtr pTop );
void printStack( StackNodePtr pCurrent );


int main(void)
{
    char sInput[BUFFER_SIZE];
    StackNodePtr pStack = NULL;
    char *pToken = NULL;
    int iIndex;

    printf("Please enter a word to be tokenized\n");

    fgets(sInput, BUFFER_SIZE, stdin);

    pToken = strtok(sInput, ", ");

    while(pToken != NULL)
    {
        push(&pStack, pToken);
        pToken = strtok(NULL, " ,");
    }

    while (isEmpty(pStack) == 0)
    {
        printf("%s\n", pop(&pStack));
    }
    return 0;
}

// Insert a node at the stack top
void push( StackNodePtr *pTop, char *cInfo )
{ 
   StackNodePtr pNew;

   pNew = malloc( sizeof( StackNode ) );

   if ( pNew != NULL )
   {   
      pNew->cData = cInfo;
      pNew->pNext = *pTop; // insert at top of stack
      *pTop = pNew;
   }
   else
   {
      printf( "%d not inserted. No memory available.\n", cInfo );
   }
} 

// Remove a node from the stack top
char* pop( StackNodePtr *pTop )
{ 
   StackNodePtr pTemp;
   char *cPopValue;

   pTemp = *pTop; // attach a pointer to element to be removed
   cPopValue = ( *pTop )->cData; 
   *pTop = ( *pTop )->pNext; // remove at top of stack
   free( pTemp ); // release this memory and set it free!

   return cPopValue;
}

int isEmpty( StackNodePtr pTop )
{ 
   return pTop == NULL;
} 

Ответы [ 3 ]

2 голосов
/ 16 февраля 2012

Когда вы используете fgets, вы читаете строку , включая '\n' в конце. когда вы токенизируете строку, этот '\n' находится в последнем токене. когда вы печатаете этот токен, вы также печатаете '\n'. Вы должны удалить его вручную или использовать scanf.

РЕДАКТИРОВАТЬ: от man fgets:

Reading stops after an EOF or a newline.
If a newline is read, it is stored into the  buffer.
0 голосов
/ 16 февраля 2012

Символ перевода строки появляется из функции fgets, когда вы заканчиваете вводить строку.См. Ссылку здесь :

Считывает символы из потока и сохраняет их в виде строки C в строке str до тех пор, пока (num-1) символы не будут прочитаны, либо не будет либо новая строка, либоКонец файла достигнут, что наступит раньше. Символ новой строки заставляет fgets перестать читать, но он считается допустимым символом, и поэтому он включен в строку, скопированную в str. Нулевой символ автоматически добавляется в str после символов, прочитанных, чтобы обозначить конецстрока С.

0 голосов
/ 16 февраля 2012

Я попытался запустить ваш код, и из того, как он выглядит, он печатает символ новой строки, который появляется, когда вы нажимаете ввод для отправки ввода.

Поскольку ваш код выталкивает их из стека и печатает токены в обратном порядке, символ новой строки, который был на последнем токене, все еще там, поэтому он всегда является новой строкой после вашего первого токена.

...