2012-08-13 3 views
0

У меня есть строка данныхРазбор данных с использованием strtok

211L CRYST1 60.970 60.970 97.140 90.000 90.000 120.000 P 32 2 1   6 

, что я хочу, чтобы разобрать в C. В частности, я хочу, чтобы извлечь P 32 2 1 в виде одной строки.

Когда я использую strtok использует все белое пространство как разделители давая мне обратно отдельные строки

P 
32 
2 
1 

Более краткая постановка вопроса:

Если у меня есть переменное число строк (4 в этом случае), как я могу объединить их в одну строку?

Мой код до сих пор:

while (fgets(line,sizeof line, PDBlist)!=NULL) 
{ 
    p=0; 
    pch=strtok(line,"\t"); 
    sprintf(space[p],"%s",pch); 

    while(pch!=NULL){ 
     pch=strtok(NULL," "); 
     p++; 
     sprintf(space[p],"%s",pch); 

    } 

for(i=8;i<(p-1);i++){ 

     if(i==(p-2))printf("%s\n",space[i]); 
     else printf("%s ",space[i]); 

     } }* 
+1

Можете ли вы опубликовать код, который у вас есть на данный момент? Это облегчит людям помощь. – hmjd

+0

Любые конкретные ограничения на формат? Или вы можете использовать также подстроку (s, 143, 11)? –

+0

Если формат входной строки является статическим, 'sscanf()' будет полезен и может с минимальными усилиями обеспечить уровень валидации (для 'float' и количество ожидаемых токенов). – hmjd

ответ

1

Если формат строк всегда как пример отвечал, альтернатива использованию strtok() будет sscanf(). Он обеспечивает уровень проверки для содержимого строки без дополнительного кодирования (например, тестирующих float значения):

const char* input = "211L CRYST1 ...."; 
char first_token[32]; 
char second_token[32]; 
float float_1, float_2, float_3, float_4, float_5, float_6; 
char last_token[32]; 

/* The '%31s' means read next sequence of non-whitespace characters 
    but don't read anymore than 31. 31 is used to leave space 
    for terminating NULL character. 

    '%f' is for reading a float. 

    '%31[^\n]' means read next sequence of characters up to newline 
    but don't read anymore than 31. */ 
if (9 == sscanf(input, "%31s %31s %f %f %f %f %f %f %31[^\n]", 
       first_token, 
       second_token, 
       &float_1, 
       &float_2, 
       &float_3, 
       &float_4, 
       &float_5, 
       &float_6, 
       last_token)) 
{ 
    /* Successfully read 9 tokens. */ 
} 

Посмотреть онлайн демо на http://ideone.com/To4ZP.

0

Спасибо за помощь!

Это решение, которое я придумал:

Если у вас есть переменное количество маркеров сначала создать массив с каждого маркера:

while(pch!=NULL){ 
       pch=strtok(NULL," "); 
       p++; 
       sprintf(space[p],"%s ",pch);  

      } 

извлечения лексем вы хотите, и объединить их в одну строку, сначала используя strcpy, а затем используя strcat

for(i=8;i<(p-1);i++){ 


       if(i==8)strcpy(dummy,space[i]); 
       else strcat(dummy,space[i]); 

      } 

Еще раз спасибо! Я думаю, что я поставил проблему Путь более запутанной в вопросе о том, что это оказалось. Если у Вас есть предложения, пожалуйста, дайте мне знать.

0

E.g.

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

int main(){ 
    char line[128] = "211L CRYST1 60.970 60.970 97.140 90.000 90.000 120.000 P 32 2 1   6\n"; 
    char field8_11[32]; 
    char *p, *field[13]; 
    int i=0; 
    for(p=line;NULL!=(p=strtok(p," \t\n"));p=NULL){ 
     field[i++]=p; 
    } 
    sprintf(field8_11, "%s %s %s %s", field[8], field[9], field[10], field[11]); 
    printf("%s\n", field8_11); 
    return 0; 
} 
Смежные вопросы