【问题标题】:How to put TEdit data into String C++ Builder如何将 TEdit 数据放入 String C++ Builder
【发布时间】:2015-07-17 09:44:11
【问题描述】:

我是编程新手。实际上,我在大学二年级并开始实习。他们希望我在 C++ builder 中做一个程序,但我只知道 C。我学了什么。而且我对OOP一无所知。

所以我的问题是。

我有 TEdit1,我想验证该文本框中引入的数据是否为数字。我知道要验证它是否是一个数字,但我不知道如何将 TEdit 中的数据放入字符串。

我写了一些代码,但它不起作用。

void __fastcall TForm1::Button1Click(TObject *Sender) 
{
    int Size = Edit1->GetTextLen(); //Get length of string in Edit1
    Size++;                         //Add room for null character
    Char *Buffer = new Char[Size];  //Creates Buffer dynamic variable

    std::auto_ptr<Char> Buffer(new Char[Size]);

    Edit1->GetTextBuf(Buffer.get(),Size); //Puts Edit1->Text into Buffer

    ShowMessage(Buffer);
}

我得到了这些错误:

 E2034 Cannot convert 'std::auto_ptr<wchar_t>' to 'UnicodeString'
 E2342 Type mismatch in parameter 'Msg' (wanted 'const UnicodeString', got              std::auto_ptr<wchar_t>')

您能否解释一下我做错了什么,或者我在哪里可以找到 Embarcadero C++ Builder 教程?我搜索了所有谷歌并没有找到可以帮助我的东西。

【问题讨论】:

    标签: c++builder c++builder-xe7


    【解决方案1】:

    你的代码有几个错误:

    1. 您在同一范围内声明了两个 Buffer 变量。这是不允许的。您需要删除其中一个。

    2. 您将std::auto_ptr 本身传递给ShowMessage(),但它需要System::UnicodeString,因此编译器错误消息。您可以使用std::auto_ptr::get() 方法获取wchar_t* 指针并将其传递给ShowMessage(),因为UnicodeString 有一个接受wchar_t* 作为输入的构造函数:

      ShowMessage(Buffer.get());
      
    3. 尽管如此,您实际上不能将来自new[] 的指针与std::auto_ptr 一起使用。 std::auto_ptr 使用 delete 而不是 delete[] 来释放指向的内存。您必须始终将deletenew 一起使用,并将delete[]new[] 一起使用。因此,虽然代码可以编译,但它不会在运行时正确释放内存。 C++11 引入了一个新的std::unique_ptr 类来替换std::auto_ptr,并且std::unique_ptr 支持new[]delete[](但是,C++Builder 的 32 位编译器还不支持 C++11——即在作品 - 但它的 64 位编译器可以):

      #include <memory>
      
      void __fastcall TForm1::Button1Click(TObject *Sender) 
      {
          int Size = Edit1->GetTextLen(); //Get length of string in Edit1
          Size++;                         //Add room for null character
      
          std::unique_ptr<Char[]> Buffer(new Char[Size]); //Creates Buffer dynamic variable
      
          Edit1->GetTextBuf(Buffer.get(), Size); //Puts Edit1->Text into Buffer
      
          ShowMessage(Buffer.get());
      }
      

    现在,话虽如此,如果您要继续使用 C++Builder,您应该学习如何使用其内置功能,例如 RTL/VCL 严重依赖的 UnicodeString(使用 @大多数代码的别名为 987654359@,仅在绝对必要时直接使用UnicodeString

    使用TEdit::Text 属性可以大大简化您的示例:

    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        String s = Edit1->Text; //Get string in Edit1
        ShowMessage(s);
    }
    

    解决问题的最简单方法是使用TCSpinEdit 组件而不是TEdit,因为TCSpinEdit 首先只允许输入数字,并且有一个Value 属性返回int

    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        int number = CSpinEdit1->Value;
        ShowMessage("It is a number");
        // use number as needed...
    }
    

    但是,如果您必须坚持使用 TEdit,有很多方法可以检查 UnicodeString 的数字内容。

    您可以将TEdit::NumbersOnly 属性设置为true,这样用户就不能输入非数字值(除非他们使用复制/粘贴,但我们暂时忽略它),然后使用RTL 的StrToInt() 函数,或System::UnicodeString::ToInt() 方法,按原样转换:

    #include <System.SysUtils.hpp>
    
    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        int number;
    
        try
        {
            number = StrToInt(Edit1->Text);
            // or: number = Edit1->Text.ToInt();
        }
        catch (const EConvertError&)
        {
            // not a number, do something else...
            ShowMessage("It is not a number");
            return;
        }
    
        ShowMessage("It is a number");
        // use number as needed...
    }
    

    或者你可以使用 RTL 的System::Sysutils::TryStrToInt() 函数:

    #include <System.SysUtils.hpp>
    
    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        int number;
    
        if (TryStrToInt(Edit1->Text, number))
        {
            // use number as needed...
            ShowMessage("It is a number");
        }
        else
        {
            // not a number, do something else...
            ShowMessage("It is not a number");
        }
    }
    

    或者您可以使用 STL 的 std::wistringstream 类:

    #include <sstream>
    
    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        int number;
    
        std::wistringstream iss(Edit1->Text.c_str());
        if (iss >> number)
        {
            // use number as needed...
            ShowMessage("It is a number");
        }
        else
        {
            // not a number, do something else...
            ShowMessage("It is not a number");
        }
    }
    

    或者,由于您有 C 背景,您可以使用 C _wtoi() 函数(在错误检查方面提供的功能不多):

    #include <cstdlib>
    
    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        int number = std::_wtoi(Edit1->Text.c_str());
        if (number != 0)
        {
            // use number as needed...
            ShowMessage("It is a valid number");
        }
        else
        {
            // not a number, do something else...
            ShowMessage("It is not a valid number");
        }
    }
    

    或者你可以使用C wcstol() 函数:

    #include <cstdlib>
    
    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        String s = Edit1->Text;
        Char *p = s.c_str(), *end;
        int number = std::wcstol(p, &end, 10);
        if (end != p)
        {
            // use number as needed...
            ShowMessage("It is a number");
        }
        else
        {
            // not a number, do something else...
            ShowMessage("It is not a number");
        }
    }
    

    或者你可以使用C swscanf() 函数:

    #include <cstdio>
    
    void __fastcall TForm1::Button1Click(TObject *Sender) 
    {
        int number;
    
        if (std::swscanf(Edit1->Text.c_str(), L"%d", &number) == 1)
        {
            // use number as needed...
            ShowMessage("It is a number");
        }
        else
        {
            // not a number, do something else...
            ShowMessage("It is not a number");
        }
    }
    

    【讨论】:

    • XE5 的 bcc32 有std::unique_ptr。它不太合规(在 C++11 允许不完整类型的某些情况下,它要求其模板参数是完整类型)但对于许多用途来说已经足够了,包括 pImpls
    • ShowMessage( Edit1-&gt;Text ); 将是另一种选择
    • @MattMcNabb:当然,这将解决 Cantor 给出的具体示例,但不是 Cantor 试图解决的总体任务。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-04-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多