3

他のものではなく、ダブルを持っていることを確認するにはどうすればよいですか?

int main() {
    int flagOk = 0;
    double number;
    while(!flagOk) {
        printf("Put in a double");
        scanf("%lf", &number);
        if(number == "%lf"); //this want make sure
        flagOk = 1;
    }
}
4

3 に答える 3

8

からの戻り値を確認してくださいscanf()。変換が成功した回数がわかります。

コンテキストでは、変換が失敗した場合は 0 になります。成功した場合は 1 を取得します。

エラー回復について考える必要があります。fgets()私は通常、 (決して gets()!を使用して) データ行を読み取り、それを で処理する方が簡単だと思いますsscanf()。変換に失敗した場合、誤ったデータを破棄するのは簡単です。

于 2009-11-05T16:43:32.137 に答える
3

ユーザーが予想する値が、文字列をatof(str)に渡すことによって返される値(指数表記を含む)と一致することを確認したい場合は、次のコードが機能します。

fgets(str、size、stdin)を使用して入力を取得でき、文字列をパーサーに渡す前に末尾の改行を削除する必要もありません。

また、解析エラーが発生した場合、関数は、追加の引数として渡されたポインターに、原因となる文字の場所を報告します。

読みやすい長い形式と入力しやすい短い形式があります。

長い形式:


/*
    Copyright (C) 2010  S. Randall Sawyer

This code is in the public domain.  It is intended to be usefully illustrative.
It is not intended to be used for any particular application. If this code is
used in any application - whether open source or proprietary, then please give
credit to the author.

*/

#include  <ctype.h>

#define FAILURE (0)
#define SUCCESS (!FAILURE)

enum {
  END_EXPRESSION        = 0x00,
  ALLOW_POINT           = 0x01,
  ALLOW_NEGATIVE        = 0x02,
  REQUIRE_DIGIT         = 0x04,
  ALLOW_EXPONENT        = 0x08,
  HAVE_EXPONENT         = 0x10,
  EXPECT_EXPRESSION     = ALLOW_POINT | ALLOW_NEGATIVE | REQUIRE_DIGIT,
  EXPECT_INTEGER        = ~ALLOW_POINT,
  EXPECT_POS_EXPRESSION = ~ALLOW_NEGATIVE,
  EXPECT_POS_INTEGER    = EXPECT_INTEGER & EXPECT_POS_EXPRESSION,
  EXPECT_EXPONENT       = EXPECT_INTEGER ^ HAVE_EXPONENT,
  EXPONENT_FLAGS        = REQUIRE_DIGIT | ALLOW_EXPONENT | HAVE_EXPONENT
} DoubleParseFlag;

int double_parse_long ( const char * str, const char ** err_ptr )
{
  int ret_val, flags;
  const char * ptr;

  flags = EXPECT_EXPRESSION;
  ptr   = str;

  do  {

    if ( isdigit ( *ptr ) ) {
      ret_val = SUCCESS;
      /*  The '+' here is the key:  It toggles 'ALLOW_EXPONENT' and
          'HAVE_EXPONENT' successively  */
      flags = ( flags + ( flags & REQUIRE_DIGIT ) ) & EXPECT_POS_EXPRESSION;
    }
    else if ( (*ptr & 0x5f) == 'E' )  {
      ret_val = ( ( flags & ( EXPONENT_FLAGS ) ) == ALLOW_EXPONENT );
      flags = EXPECT_EXPONENT;
    }
    else if ( *ptr == '.' ) {
      ret_val = ( flags & ALLOW_POINT );
      flags = ( flags & EXPECT_POS_INTEGER );
    }
    else if ( *ptr == '-' ) {
      ret_val = ( flags & ALLOW_NEGATIVE );
      flags = ( flags & EXPECT_POS_EXPRESSION );
    }
    else if ( iscntrl ( *ptr ) )  {
      ret_val = !( flags & REQUIRE_DIGIT );
      flags = END_EXPRESSION;
    }
    else  {
      ret_val = FAILURE;
      flags = END_EXPRESSION;
    }

    ptr++;

  } while (ret_val && flags);

  if (err_ptr != NULL)
    *err_ptr = ptr - 1;

  return ret_val;
}

ショートフォーム:


/*
    Copyright (C) 2010  S. Randall Sawyer

This code is in the public domain.  It is intended to be usefully illustrative.
It is not intended to be used for any particular application. If this code is
used in any application - whether open source or proprietary, then please give
credit to the author.

*/

#include  <ctype.h>

int double_parse_short ( const char * str, const char ** err_ptr )
{
  int ret_val, flags;
  const char * ptr;

  flags = 0x07;
  ptr   = str;

  do  {

    ret_val = ( iscntrl ( *ptr ) ) ? !(flags & 0x04) : (
              ( *ptr == '.' ) ? flags & 0x01 : (
              ( *ptr == '-' ) ? flags & 0x02 : (
              ( (*ptr & 0x5f) == 'E' ) ? ((flags & 0x1c) == 0x08) : (
              ( isdigit ( *ptr ) ) ? 1 : 0 ) ) ) );

    flags =   ( isdigit ( *ptr ) ) ?
                (flags + (flags & 0x04)) & 0x1d : (
              ( (*ptr & 0x5f) == 'E' ) ? 0x0e : (
              ( *ptr == '-' ) ? flags & 0x1d : (
              ( *ptr == '.' ) ? flags & 0x1c : 0 ) ) );

    ptr++;

  } while (ret_val && flags);

  if (err_ptr != NULL)
    *err_ptr = ptr - 1;

  return ret_val;
}

これがお役に立てば幸いです。

于 2010-05-14T12:14:18.233 に答える
3

おそらく、次のようなコード フラグメントが必要になるでしょう。

double number;
do {
    printf("Enter a double: ");
    scanf("%*c"); // burn stdin so as not to buffer up responses
} while (1 != scanf("%lf", &number));

ただし、Jonathan が指摘したように、行ごとの解析を改善した方がよい場合があります。この方法で直接スキャンするstdinことは、ユーザーにとって直感的ではありません。

于 2009-11-05T17:07:55.490 に答える