1

C ++のunistd.hに含まれている関数を使用してgetopt、次のようにoptstringを構造化する方法があります...

[-a] [-f "reg_expr"] out_file1 [[-f "reg_expr"] out_file2 ...]可能です?

これは宿題ですが、この特定のサブタスクには重点が置かれていません。

私の頭の中で、次のロジックを指定したいと思います。

(引数)、(2つの必要な(サブ)引数を持つ無限に多くのf引数)、...(無限に多くの一般的な引数)

おそらく、getopt機能についての私の理解は根本的に欠陥があります。私も見ましたgetopt_long。おそらくそれが私が欠けているものです。

私はもともとこれをドラフトしましたが、それはうまくいきましたが、私はその関数に出くわし、getoptそれがより良い仕事をするかもしれないと思いました。

int outFileFlags;
int outFileMode = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH;
int i = 1;
while (i < argc){
    if (i == 1 && strcmp( argv[i], "-a") == 0){
        cout << "append flag set" << endl;
        outFileFlags = O_RDWR | O_APPEND;
        i++;
        continue;
    }
    else {
        outFileFlags = O_TRUNC | O_RDWR | O_CREAT;
    }
    if (strcmp( argv[i], "-f") == 0 && i+2 <= argc){
        cout << "   regx = " << argv[i+1] << endl;
        cout << "   fn = " << argv[i+2] << endl;
        i = i+3;
        continue;
    }
    else {
        cout << "   regx = none" << endl;
        cout << "   fn = " << argv[i] << endl;
        i++;
        continue;
    }
}

注:これはUNIX環境用に作成されていると想定してください。標準ライブラリからは何も使えないと思います。テスト目的でstd::coutのみを含めました。

課題の詳細については、喜んで詳しく説明させていただきます。ただし、主な質問はoptstringの構文を中心に展開します。私は現在、:必須の意味と::オプションの意味のみを認識しています。正規表現のワイルドカード*のように繰り返す引数を指定する方法はありますか?

編集:

getoptがオプションごとに複数の引数を処理するように設計されているとは思わないという事実のために、これはずさんだと確信していますが、それはトリックを行います...

int main(int argc, char *argv[]){
    char c;
    int iterations = 0;
    while (*argv) {
        optind = 1;
        if (iterations == 0){
            opterr = 0;
            c = getopt(argc, argv, "a");
            if(c == 'a'){
                //~ APPEND SET
            }
            else if(c=='?'){
                optind--;
            }
        }
        while ((c = getopt(argc, argv, "f:")) != -1) {
            if (c == 'f'){
                //~ REGEX = optarg
                if (optind < argc && strcmp(argv[optind], "-f") != 0) {
                    //~ FILENAME = argv[optind]
                    optind++;
                }
                else {
                    errno = 22;
                    perror("Error");
                    exit(errno);
                }
            }
            else {
                errno = 22;
                perror("Error");
                exit(errno);
            }
        }
        argc -= optind;
        argv += optind;
        iterations++;
        //~ REMAINING FILES = *argv
    }
}
4

1 に答える 1

1

オプションと出力ファイル名のグループごとに個別のgetoptループを実行する必要があります。

group_index = 0;
while (*argv) {
  optreset = 1;
  optind = 1;
  while ((ch = getopt(argc, argv, "af:")) != -1) {
    switch (ch) {
      /* process options */
    }
  }
  argc -= optind;
  argv += optind;
  outfile[group_index++] = *argv;
  argc--;
  argv++;
}
于 2012-11-19T05:24:10.440 に答える