0

だから私は多くの人がこれを尋ねるのを見てきましたが、ウェブの周りに浮かんでいる確かな答えはあまりありません。ほとんどの場合、文字列の代わりに整数が配置されていることを確認しますが、浮動小数点数が入力された場合は下半分が切り捨てられ、整数と文字が挿入されている場合は文字が切り捨てられます。ユーザー入力をチェックし、入力が無効であるか、有効/無効の組み合わせであるかどうかをユーザーに再試行するように求めるコードを書くのに助けが必要です。基本的な考え方は、文字列を作成して何でも受け入れるようにし、sstreamを使用して操作し、入力が正当な場合はintに戻ることでしたが、他の部分を実際にチェックすることはできません。誰かがこれに出くわしたり、私を助けてくれるなら、私をそれにリンクしてください。何をすべきかがよくわかったら、コードを投稿します。

4

4 に答える 4

2

を使用できないと仮定してboost::lexical_cast、独自のバージョンを作成できます。

#include <sstream>
#include <iostream>
#include <stdexcept>
#include <cstdlib>
template <class T1, class T2>
T1 lexical_cast(const T2& t2)
{
  std::stringstream s;
  s << t2;
  T1 t1;
  if(s >> std::noskipws >> t1 && s.eof()) {
    // it worked, return result
    return t1;
  } else {
    // It failed, do something else:
    // maybe throw an exception:
    throw std::runtime_error("bad conversion");
    // maybe return zero:
    return T1();
    // maybe do something drastic:
    exit(1);
  }
}



int main() {
  std::string smin, smax;
  int imin, imax;

  while(std::cout << "Enter min and max: " && std::cin >> smin >> smax) {
    try {
      imin = lexical_cast<int>(smin);
      imax = lexical_cast<int>(smax);
      break;
    } catch(std::runtime_error&) {
      std::cout << "Try again: ";
      continue;
    }
  }

  if(std::cin) {
    std::cout << "Thanks!\n";
  } else {
    std::cout << "Sorry. Goodbye\n";
    exit(1);
  }
}
于 2013-03-07T15:45:20.917 に答える
2

stol のようなC++11文字列変換関数を使用できます

try
{
    std::string value = ...;
    long number = std::stol(value); 
}
catch (std::invalid_argument const& e)
{
    // no conversion could be performed
}

コメント後の更新: Visual Studio 2012 に同梱されている Visual C++ 11は、 で宣言さstd::stolれた便利なラッパーとして実装されています。ほとんどの C++11 実装では、機械に到達するのではなく、可能な限り最適な方法で定義されていると想定しても安全だと思います。strtol<cstdlib>std::stringstream

于 2013-03-07T15:53:02.890 に答える
1

C 関数strtol(およびその兄弟) は、渡された文字列が完全に消費されたかどうかを通知できます。

 std::string str;
 char *endptr;
 std::cin >> str;
 long x = std::strtol(str.c_str(), &endptr, 0); 
 if (*endptr != 0) 
    cout << "That's not a valid number...";
于 2013-03-07T15:40:41.513 に答える
0

Javaのようにプリミティブ型をカプセル化するクラスが標準のc++libにあるかどうかはわかりませんが、ここでは、単純で非常に基本的な実装がどのように見えるかを示します。

class Integer {
   private:
       int value;
       void parse(string);
   public:
       Integer(string);
       int intValue();
};

Integer::Integer(string sint) { parse(sint); }
int Integer::intValue() { return value; }

void Integer::parse(string sint) {
    string::iterator its = sint.begin();
    while(its != sint.end() && (! (*its < '0' || *its > '9'))) {
        its++;
    }
    if(its != sint.end()) {
        throw sint + ": Input is not a valid integer.";
    }
    value = atoi(sint.c_str());
}
于 2013-03-07T16:25:25.390 に答える