реклама на сайте
подробности

 
 
 
Reply to this topicStart new topic
> Как из текстовой строки вытащить подстроку, после определенного шаблона?
Димон Безпарольн...
сообщение Sep 7 2017, 14:06
Сообщение #1


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Есть допустим строка:

Код
unsigned char HTTPStr[] = "setting.html?SSID=sd&PASSWORD=dsd&NOTE=sds";



Нужно вытащить из нее sd и dsd.

Делаю так:

Код
int LeechPar(char* SrsBuf, char* Template, char* DestBuf)

{
    int T = strstr((const char*)SrsBuf, Template) + (strlen(Template));
    if(!T) {return 0;}
    int T1 = strstr((const char*)T,"&");
    if(!T1) {return 0;}
    int T2 = T1 - T;
        if(T2 > 20){return 0;}
    memcpy(DestBuf, T, T2);
    DestBuf[T2] = 0;
    return T2;
}

int main (void)
{    

    char Buf[20];

    //int T = strstr((const char*)HTTPStr,"SSID=") + 5;
    //int T1 = strstr((const char*)T,"&");
    //memcpy(Buf, T, T1 - T);
    //Buf[T1 - T] = 0;
    
    int P = LeechPar(HTTPStr, "SSID=", Buf);
    printf("\n%s %d\n", Buf, P);            

    P = LeechPar(HTTPStr, "PASSWORD=", Buf);
    printf("\n%s %d\n", Buf, P);    

}


Какие могут быть подводные камни? И может быть есть способ проще?

Сообщение отредактировал Димон Безпарольный - Sep 7 2017, 14:16
Go to the top of the page
 
+Quote Post
scifi
сообщение Sep 7 2017, 14:21
Сообщение #2


Гуру
******

Группа: Свой
Сообщений: 2 737
Регистрация: 7-02-07
Пользователь №: 25 136



Код
sscanf(HTTPStr, "setting.html?SSID=[^&]&PASSWORD=[^&]", ssid, pass);
Go to the top of the page
 
+Quote Post
Димон Безпарольн...
сообщение Sep 7 2017, 15:02
Сообщение #3


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Если так, то что - то не получается:

Код
    char ssid[20];
    char pass[20];    
    sscanf(HTTPStr, "setting.html?SSID=[^&]&PASSWORD=[^&]", ssid, pass);
    printf("\n%s\n", ssid);


Но идея хорошая. Это работает:

Код
#include <math.h>
#include <stdio.h>
#include <stdlib.h>

char *tokenstring = "first,25.5,second,15";
int result, i;
double fp;
char o[10], f[10], s[10], t[10];

void main()
{
   result = sscanf(tokenstring, "%[^','],%[^','],%[^','],%s", o, s, t, f);
   fp = atof(s);
   i  = atoi(f);
   printf("%s\n %lf\n %s\n %d\n", o, fp, t, i);
}
Go to the top of the page
 
+Quote Post
aaarrr
сообщение Sep 7 2017, 15:09
Сообщение #4


Гуру
******

Группа: Свой
Сообщений: 10 173
Регистрация: 11-12-04
Пользователь №: 1 448



Цитата(Димон Безпарольный @ Sep 7 2017, 18:02) *
Но идея хорошая.

Плохая: контроля переполнения нет, а чудес у вас и без того хватает, как можно было заметить.
Go to the top of the page
 
+Quote Post
Димон Безпарольн...
сообщение Sep 7 2017, 15:11
Сообщение #5


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Цитата(aaarrr @ Sep 7 2017, 19:09) *
Плохая: контроля переполнения нет, а чудес у вас и без того хватает, как можно было заметить.

Нда. Возможно так. Если других способов нет... Мой то наверно не лучше.

Сообщение отредактировал Димон Безпарольный - Sep 7 2017, 15:13
Go to the top of the page
 
+Quote Post
aaarrr
сообщение Sep 7 2017, 15:17
Сообщение #6


Гуру
******

Группа: Свой
Сообщений: 10 173
Регистрация: 11-12-04
Пользователь №: 1 448



Цитата(Димон Безпарольный @ Sep 7 2017, 18:11) *
Мой то наверно не лучше.

Ну, если ошибки убрать, то ничего. Сейчас причешем.
Go to the top of the page
 
+Quote Post
Димон Безпарольн...
сообщение Sep 7 2017, 15:19
Сообщение #7


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Некоторые убрал:

Код
unsigned char HTTPStr[] = "+IPD,0,471:GET /setting.html?SSID=77&PASSWORD=5 HTTP/1.1";

int LeechPar(char* SrsBuf, char* Template, char* Template1, char* DestBuf)

{
    int T = strstr((const char*)SrsBuf, Template);
    if(!T) {return 0;}
    T = T + (strlen(Template));
    int T1 = strstr((const char*)T, Template1);
    if(!T1) {return 0;}
    int T2 = T1 - T;
    if(T2 > 20){return 0;}
    memcpy(DestBuf, T, T2);
    DestBuf[T2] = 0;
    return T2;
}

int main (void)
{    

    char Buf[20];
    
    int P = LeechPar(HTTPStr, "SSID=", "&", Buf);
    printf("\n%s %d\n", Buf, P);            

    P = LeechPar(HTTPStr, "PASSWORD=", " HTTP", Buf);
    printf("\n%s %d\n", Buf, P);    

}


Сообщение отредактировал Димон Безпарольный - Sep 7 2017, 15:21
Go to the top of the page
 
+Quote Post
aaarrr
сообщение Sep 7 2017, 15:29
Сообщение #8


Гуру
******

Группа: Свой
Сообщений: 10 173
Регистрация: 11-12-04
Пользователь №: 1 448



Цитата(Димон Безпарольный @ Sep 7 2017, 18:19) *
Некоторые убрал:

4 warning'а, 1 note и Segmentation Fault на 64 битной машине...

Проще надо быть:
Код
#include <stdio.h>
#include <string.h>

unsigned char HTTPStr[] = "setting.html?SSID=sd&PASSWORD=dsd&NOTE=sds";

int LeechPar(char* SrsBuf, char* Template, char* DestBuf, int n)
{
    char *src = strstr((const char*)SrsBuf, Template), c;
    int i;

    if(src)
    {
        src += strlen(Template);
        for(i = 0; i < n; i++)
        {
            c = src[i];
            if(c)
            {
                if(c == '&')
                {
                    DestBuf[i] = '\0';
                    return i;
                }
                DestBuf[i] = c;
            }
            else return 0;
        }
    }
    return 0;
}

int main(int argc, char *argv[])
{    
    char Buf[20];

    int P = LeechPar(HTTPStr, "SSID=", Buf, sizeof(Buf));
    printf("\n%s %d\n", Buf, P);            

    P = LeechPar(HTTPStr, "PASSWORD=", Buf, sizeof(Buf));
    printf("\n%s %d\n", Buf, P);    

}
Go to the top of the page
 
+Quote Post
Димон Безпарольн...
сообщение Sep 7 2017, 15:41
Сообщение #9


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Сломал голову, что такое с и чему оно равно в строке:

Код
    char *src = strstr((const char*)SrsBuf, Template), c;


С исходной строкой:

Код
unsigned char HTTPStr[] = "setting.html?SSID=sd&PASSWORD=dsd&NOTE=sds";


Работает. А со строкой:
Код
unsigned char HTTPStr[] = "+IPD,0,471:GET /setting.html?SSID=5&PASSWORD=5 HTTP/1.1";


Уже нет. Выдает:

Цитата
5 1

5 HTTP/1.1  b◄kv─[pv4¶@ 0


Я добавил Template1 потому что он разный. Во втором случае он " HTTP". Видимо от сюда и глюк.

Сообщение отредактировал Димон Безпарольный - Sep 7 2017, 15:45
Go to the top of the page
 
+Quote Post
scifi
сообщение Sep 7 2017, 16:07
Сообщение #10


Гуру
******

Группа: Свой
Сообщений: 2 737
Регистрация: 7-02-07
Пользователь №: 25 136



Цитата(aaarrr @ Sep 7 2017, 18:09) *
Плохая: контроля переполнения нет

Издеваетесь? У сканфа есть средства для этого. Лень в справочник заглянуть? Или вам надо предъявить все до последней запятой? Нет уж, увольте.
Go to the top of the page
 
+Quote Post
aaarrr
сообщение Sep 7 2017, 16:34
Сообщение #11


Гуру
******

Группа: Свой
Сообщений: 10 173
Регистрация: 11-12-04
Пользователь №: 1 448



Цитата(scifi @ Sep 7 2017, 19:07) *
Издеваетесь? У сканфа есть средства для этого. Лень в справочник заглянуть? Или вам надо предъявить все до последней запятой? Нет уж, увольте.

Берегите нервы. Идея нормальная, реализация - увы.

Цитата(Димон Безпарольный @ Sep 7 2017, 18:41) *
Сломал голову, что такое с и чему оно равно в строке:

Код
    char *src = strstr((const char*)SrsBuf, Template), c;

Переменная типа char. Ничему не равна.

Цитата(Димон Безпарольный @ Sep 7 2017, 18:41) *
С исходной строкой:

Код
unsigned char HTTPStr[] = "setting.html?SSID=sd&PASSWORD=dsd&NOTE=sds";


Работает. А со строкой:
Код
unsigned char HTTPStr[] = "+IPD,0,471:GET /setting.html?SSID=5&PASSWORD=5 HTTP/1.1";


Уже нет.

Так определитесь с критериями определения конца поля.
Go to the top of the page
 
+Quote Post
Димон Безпарольн...
сообщение Sep 7 2017, 16:48
Сообщение #12


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Цитата(aaarrr @ Sep 7 2017, 20:34) *
Так определитесь с критериями определения конца поля.

Конец поля увы оказался разный. Для этого и Template1
Go to the top of the page
 
+Quote Post
aaarrr
сообщение Sep 7 2017, 17:17
Сообщение #13


Гуру
******

Группа: Свой
Сообщений: 10 173
Регистрация: 11-12-04
Пользователь №: 1 448



Цитата(Димон Безпарольный @ Sep 7 2017, 19:48) *
Конец поля увы оказался разный. Для этого и Template1

Подозреваю, что число вариантов все же конечное, и можно обойтись без Template1.
Go to the top of the page
 
+Quote Post
Димон Безпарольн...
сообщение Sep 7 2017, 19:58
Сообщение #14


Знающий
****

Группа: Участник
Сообщений: 601
Регистрация: 29-11-10
Пользователь №: 61 247



Цитата(aaarrr @ Sep 7 2017, 21:17) *
Подозреваю, что число вариантов все же конечное, и можно обойтись без Template1.

Я пока и сам не знаю сколько их.
Go to the top of the page
 
+Quote Post
timurey
сообщение Sep 8 2017, 07:25
Сообщение #15





Группа: Участник
Сообщений: 9
Регистрация: 10-05-07
Пользователь №: 27 628



Довольно простой парсер (взято отсюда: http://we.easyelectronics.ru/electro-and-p...ttp-i-cgi.html)

Код
char *url, *p, *params,

// Разбираем URL на путь и параметры
if((params = strchr(url, '?')))
    *(params++) = 0;

// Разбираем параметры
while(params)
{
     // Смотрим где заканчивается параметр
    if((p = strchr(params, '&')))
        *(p++) = 0;
                
    // Разбираем параметр на имя и значение
    name = params;
    if((value = strchr(name, '=')))
        *(value++) = 0;
                
    // Параметр = led (on/off)?
    if( (strcmp(name, "led") == 0 ) && value )
    {
        if(strcmp(value, "on") == 0)
            led_on()
        else if(strcmp(value, "off") == 0)
            led_off()
     }
                
     // Параметр = lang (en/ru)?
     else if( (strcmp_P(name, PSTR("lang")) == 0) && value )
     {
         if(strcmp_P(value, "en") == 0)
             lang_ru = 0;
         else if(strcmp_P(value, "ru") == 0)
             lang_ru = 1;
      }
                
      // Переходим к следующему параметру
      params = p;
}


--------------------
timurey.
Go to the top of the page
 
+Quote Post

Reply to this topicStart new topic
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 20th September 2017 - 16:39
Рейтинг@Mail.ru


Страница сгенерированна за 0.01535 секунд с 7
ELECTRONIX ©2004-2016