1

次のようないくつかの入力パラメータがあります。

param1 = param1Value & param2 = param2Value & param3 = param3Value ...

これらのパラメータは文字「&」でリンクされ、パラメータとその値は「=」でリンクされます。それらを次のようなキー値マップに解析したい:

[param1, param1Value], [param2, param2Value], [param3, param3Value],...

ただし、パラメーターの値には2 つのkey-charactersが含まれているため、パラメーター解析手順が中断されます。

sprintfを使用して別のアプリケーションのパラメーター値を変更するなど、これらのパラメーター形式を簡単にカスタマイズできるように作成したパラメーター パサーに通知されました。そのため、これらのパラメーターをマップ配列で区切るよう説得するのは困難です。

本来は yacc/lex を使うつもりだったのですが、ちょっとした機能が複雑すぎます。sscanfは、正規表現のようなテキストを解析することもできますが、私のパラメーター リストに対して正規表現のような文字列を作成するのはそれほど簡単ではないようです。

キー文字なしでそれらを解析する簡単だが信頼できる方法はありますか?

4

3 に答える 3

6

を使用strtokして文字列をトークン化し'&'、「トークン」を分割し'='てパラメータ名と値を取得できます。

at での分割は、 as well (またはむしろ) を使用するか、and /または/'='を使用して行うことができます。strtokstrtok_rstrchrstrncpystrcpystrndupstrdup

于 2012-04-13T07:10:11.323 に答える
0

そのパターンが保証されている場合は、単純な解析関数を使用できます。

キー/値の最大長が保証されている場合は、固定バッファー+コピーが最も簡単です。それ以外の場合は、最初にセパレータの場所を見つけ、次にそのサイズのmallocなどを見つけることができます。

簡単なとして、最大100の固定サイズの/concept:

#include <stdio.h>

int get_pair(char **p, char *key, char *val)
{
    int esc = 0;    /* escape level */
    char *cp = key; /* current target */

    *key = '\0';    /* if either is blank */
    *val = '\0';

    if (!*p || !**p)
        return 0;

    /* this could be done more elegant */
    while (**p) {
        if (**p == '=' && (esc & 1) == 0) {
            *cp = '\0'; /* terminate */
            cp = val;   /* change target */
            ++(*p);
            continue;
        } else if (**p == '&' && (esc & 1) == 0) {
            ++(*p);     /* skip & and break */
            break;
        }

        if (**p == '\\') {
            if((++esc & 1) == 0) /* if 2, 4, 6 ... \'s */
                *cp++ = **p;
        } else {
            esc = 0;
            *cp++ = **p;
        }
        ++(*p);
    }

    *cp = '\0';
    return 1;
}

int main(void)
{
    char *data = "ab=123&a\\=42&m\\\\ed\\=\\&do\\\\\\\\=mix";
    char key[100];
    char val[100];

    printf("Parse: %s\n", data);

    while (get_pair(&data, key, val))
        printf("key: %s\nval: %s\n\n", key, val);

    return 0;
}

出力:

Parse: ab=123&a\=42&m\\ed\=\&do\\\\=mix
key: ab
val: 123

key: a=42
val: 

key: m\ed=&do\\
val: mix
于 2012-04-13T08:57:15.363 に答える
0

はい、私はそれらを修正しました: passer は私にパラメータを与えますが、それらはand\をエスケープするために使用する必要がありますが、それ自体はエスケープする必要はありません。これらのパラメーターを抽出する際に、を, および'='に置き換えただけ です。実際の値が の場合は、 でエンコードします。キャラクターを分析する必要はありません。そのままにしておくだけです。=&\\&&\=\\=\\\=\

于 2012-05-08T15:14:47.517 に答える