none
textBox1->Textを文字配列へ変換したい RRS feed

  • 質問

  • Windowsフォーム上に定義したテキストボックスへ入力された文字列 textBox1->Text の内容を

    文字配列 (例えば) char abc[16] ;

    へ変換するにはどうしたらできるでしょうか?・・・質問(1)

    次のものはコンパイルが失敗します。

    #include <string.h>

    char abc[16] ;

    strcpy(abc, (char *)textBox1->Text) ;  //castによる型変換はできないコンパイルエラーになる。

    (型がもともと合わないのは存じていますが、試しにやってみました。)

    また、似たよう問題として、 textBox1->Textに格納された”整数の文字列” を、

    整数型 int  i ; へ変換するには、どうしたらできるでしょうか? ・・・質問(2)

    何か便利に使えるAPI関数はあるでしょうか?

    よろしくお願いします。 

     

     

    2006年10月13日 8:27

回答

  • なんで char型配列を使うのでしょうか?(API、既存のDLL、MFC等を使うのでなければ出番はないと思う。)
    CLRプログラムであれば基本的に array< wchar_t >^型だと思うんだけど。
    (あってもwchar_t型配列)

    (1)
    MarshalクラスのStringToHGlobalAnsiを使って、const char*型の値を取得して、strcpyしてください。
    (別バッファに移すのを前提にするのであれば、PtrToStringCharsからconst wchar_t*型を取得して変換するのもありかな。
    Text::EncodingクラスのGetBytesからarray<Byte>^型の値を取得して、strcpyというのも。)

    (2)
    int::Parse
    int::TryParse
    Convert::ToInt32
    あたりを使って変換できます。

    もちろん、(1)の方法とかを使って、const char*型やconst wchar_t*型の値から、
    strtol,atoi,sscanf等ってのもありかもしれないけど、ムダが多いです。

    2006年10月13日 8:39
  •  蒼の洞窟 さんからの引用

    なんで char型配列を使うのでしょうか?(API、既存のDLL、MFC等を使うのでなければ出番はないと思う。)

    早速ありががとうございます。UNIX用に作成していたTCP/IPソケットを使った通信プログラム

    をWin32コンソールプログラムにして移植しました。

    それを、さらに、GUI形式(Windowsフォーム)のプログラムにするため、

    次の自作した関数で、winsock2を開けようとしているためです。

    int c_setup(char *ip_addr, int port)
    {
     WSADATA wsadata;
     WORD wversion = WINSOCK_VERSION;
     
     struct sockaddr_in server_inf;
     struct hostent *host;
     
     int nError;
     
     SOCKET client_socket = -1;   // socket

     //Winsock.dllを初期化
     nError = WSAStartup( wversion, &wsadata);
     if( nError) {
      fprintf( stderr, "WSAStartup error\n");
      return 0;
     }
     //Winsockのバージョンをチェック
     if( wversion != wsadata.wVersion) {
      fprintf( stderr, "Winsock version error\n");
      return 0;
     }

    // hostent *server_inf1;   // client information 1

     memset((char *)&server_inf, 0, sizeof(server_inf));
     server_inf.sin_family      = AF_INET;   // address family
     server_inf.sin_port        = htons(port);   // htons( 2bytes)
                                                         //specify upper and lower byte of integer
    //        if(inet_pton(AF_INET, ip_addr, &server_inf.sin_addr) <=0)
    //         printf("***error*** invalid IP address of server\n") ;

     unsigned long addr;
     addr = inet_addr( ip_addr);
     if( ( host = gethostbyaddr( (char *)&addr, sizeof( addr), AF_INET)) == NULL) {
      fprintf( stderr, "Server none\n");
        return 0;
       }
            else {
       
      memcpy( &server_inf.sin_addr, host->h_addr, host->h_length);//specify IP address to connect 

                 /* make socket */
       if ((client_socket = socket(AF_INET, SOCK_STREAM, 0)) < 0)
         printf("***error***  failed maiking socket\n");
                /* connect with a server */
       else {
            if (connect(client_socket, (sockaddr *)&server_inf, sizeof(server_inf)) == -1)
            client_socket = -1;
       }

           }
     return client_socket;
    } //この関数は、Win32コンソールで一応は正常動作しています。(できたてなので細かくはデバッグしていないです。)

    ・・・ここで、 inet_addr( ip_addr); のip_addr[ ]がchar型であるため、

    この関数に、Winプログラムのテキストボックスから入力するIPアドレス内容(文字列)を、この引数(文字配列)へ入力させたいのです。

    2006年10月13日 9:18
  •  蒼の洞窟 さんからの引用

    なんで char型配列を使うのでしょうか?(API、既存のDLL、MFC等を使うのでなければ出番はないと思う。)
    CLRプログラムであれば基本的に array< wchar_t >^型だと思うんだけど。
    (あってもwchar_t型配列)

    (1)
    MarshalクラスのStringToHGlobalAnsiを使って、const char*型の値を取得して、strcpyしてください。
    (別バッファに移すのを前提にするのであれば、PtrToStringCharsからconst wchar_t*型を取得して変換するのもありかな。
    Text::EncodingクラスのGetBytesからarray<Byte>^型の値を取得して、strcpyというのも。)

    (2)
    int::Parse
    int::TryParse
    Convert::ToInt32
    あたりを使って変換できます。

    もちろん、(1)の方法とかを使って、const char*型やconst wchar_t*型の値から、
    strtol,atoi,sscanf等ってのもありかもしれないけど、ムダが多いです。

    類似の問題の記事を見つけました。

    TITLE:Re: System::String を Char に変換する方法について - MSDNフォーラム
    URL:
    http://forums.microsoft.com/MSDN-JA/ShowPost.aspx?PostID=798561&SiteID=7

    sprintf()を使う方法ですが、皆さん優秀ですねぇ。

    今日受けたアドバイスは熟練者のテクニックであるとの記事も出てきました。

    ・・・今日は帰りますので、またあとでよろしくお願いします。

    2006年10月13日 10:43
  • char型配列に入れる例です。
    考えついただけ載せてみました。
    ただ、sprintfの方法は正攻法のやり方なのか確信できていないので載せていません。

    #include <cstring> // strcpy_s
    #include <cstdio>  // printf
    #include <clocale> // setlocal
    #include <cstdlib> // wcstombs_s
    #include <vcclr.h> // PtrToStringChars
    
    void sample1( System::String^ s )
    {
        char buff[ 256 ];
    
        System::IntPtr p
    = System::Runtime::InteropServices::Marshal::StringToHGlobalAnsi( s ); strcpy_s( buff, static_cast< const char* >( p.ToPointer() ) );
    System::Runtime::InteropServices::Marshal::FreeHGlobal( p ); printf( "sample1 : %s\n", buff ); } void sample2( System::String^ s ) { char buff[ 256 ]; array< unsigned char >^ a
    = System::Text::Encoding::GetEncoding( L"Shift_JIS" )->GetBytes( s ); pin_ptr< const unsigned char > p = &a[ 0 ]; strcpy_s( buff, static_cast<const char*>(static_cast<const void*>(p)) ); printf( "sample2 : %s\n", buff ); } void sample3( System::String^ s ) { char buff[ 256 ]; size_t ret = 0; // wchar_t wbuff[ 256 ]; pin_ptr< const wchar_t > p = PtrToStringChars( s ); // wcscpy_s( wbuff, p ); wcstombs_s( &ret, buff, p, ( wcslen( p ) + 1 ) * sizeof( wchar_t ) ); // wprintf( L"sample3 : %s\n", wbuff ); printf( "sample3 : %s\n", buff ); } void sample4( System::String^ s ) { char buff[ 256 ]; size_t ret = 0; array< wchar_t >^ a = s->ToCharArray(); pin_ptr< const wchar_t > p = &a[ 0 ]; wcstombs_s( &ret, buff, p, ( wcslen( p ) + 1 ) * sizeof( wchar_t ) ); printf( "sample4 : %s\n", buff ); } int main() { setlocale( LC_ALL, "Japanese" ); // wcstombs_sのため System::String^ s = L"あいうえおABC"; sample1( s ); sample2( s ); sample3( s ); sample4( s ); return 0; }
    2006年10月13日 11:15
  • ありがとうございます。参考にして頑張ってみます。

     追伸:

    Stringから文字列への変換が正常にできました。

    ご教示ありがとうございました。

     

    2006年10月16日 0:32

すべての返信

  • なんで char型配列を使うのでしょうか?(API、既存のDLL、MFC等を使うのでなければ出番はないと思う。)
    CLRプログラムであれば基本的に array< wchar_t >^型だと思うんだけど。
    (あってもwchar_t型配列)

    (1)
    MarshalクラスのStringToHGlobalAnsiを使って、const char*型の値を取得して、strcpyしてください。
    (別バッファに移すのを前提にするのであれば、PtrToStringCharsからconst wchar_t*型を取得して変換するのもありかな。
    Text::EncodingクラスのGetBytesからarray<Byte>^型の値を取得して、strcpyというのも。)

    (2)
    int::Parse
    int::TryParse
    Convert::ToInt32
    あたりを使って変換できます。

    もちろん、(1)の方法とかを使って、const char*型やconst wchar_t*型の値から、
    strtol,atoi,sscanf等ってのもありかもしれないけど、ムダが多いです。

    2006年10月13日 8:39
  •  蒼の洞窟 さんからの引用

    なんで char型配列を使うのでしょうか?(API、既存のDLL、MFC等を使うのでなければ出番はないと思う。)

    早速ありががとうございます。UNIX用に作成していたTCP/IPソケットを使った通信プログラム

    をWin32コンソールプログラムにして移植しました。

    それを、さらに、GUI形式(Windowsフォーム)のプログラムにするため、

    次の自作した関数で、winsock2を開けようとしているためです。

    int c_setup(char *ip_addr, int port)
    {
     WSADATA wsadata;
     WORD wversion = WINSOCK_VERSION;
     
     struct sockaddr_in server_inf;
     struct hostent *host;
     
     int nError;
     
     SOCKET client_socket = -1;   // socket

     //Winsock.dllを初期化
     nError = WSAStartup( wversion, &wsadata);
     if( nError) {
      fprintf( stderr, "WSAStartup error\n");
      return 0;
     }
     //Winsockのバージョンをチェック
     if( wversion != wsadata.wVersion) {
      fprintf( stderr, "Winsock version error\n");
      return 0;
     }

    // hostent *server_inf1;   // client information 1

     memset((char *)&server_inf, 0, sizeof(server_inf));
     server_inf.sin_family      = AF_INET;   // address family
     server_inf.sin_port        = htons(port);   // htons( 2bytes)
                                                         //specify upper and lower byte of integer
    //        if(inet_pton(AF_INET, ip_addr, &server_inf.sin_addr) <=0)
    //         printf("***error*** invalid IP address of server\n") ;

     unsigned long addr;
     addr = inet_addr( ip_addr);
     if( ( host = gethostbyaddr( (char *)&addr, sizeof( addr), AF_INET)) == NULL) {
      fprintf( stderr, "Server none\n");
        return 0;
       }
            else {
       
      memcpy( &server_inf.sin_addr, host->h_addr, host->h_length);//specify IP address to connect 

                 /* make socket */
       if ((client_socket = socket(AF_INET, SOCK_STREAM, 0)) < 0)
         printf("***error***  failed maiking socket\n");
                /* connect with a server */
       else {
            if (connect(client_socket, (sockaddr *)&server_inf, sizeof(server_inf)) == -1)
            client_socket = -1;
       }

           }
     return client_socket;
    } //この関数は、Win32コンソールで一応は正常動作しています。(できたてなので細かくはデバッグしていないです。)

    ・・・ここで、 inet_addr( ip_addr); のip_addr[ ]がchar型であるため、

    この関数に、Winプログラムのテキストボックスから入力するIPアドレス内容(文字列)を、この引数(文字配列)へ入力させたいのです。

    2006年10月13日 9:18
  •  蒼の洞窟 さんからの引用

    なんで char型配列を使うのでしょうか?(API、既存のDLL、MFC等を使うのでなければ出番はないと思う。)
    CLRプログラムであれば基本的に array< wchar_t >^型だと思うんだけど。
    (あってもwchar_t型配列)

    (1)
    MarshalクラスのStringToHGlobalAnsiを使って、const char*型の値を取得して、strcpyしてください。
    (別バッファに移すのを前提にするのであれば、PtrToStringCharsからconst wchar_t*型を取得して変換するのもありかな。
    Text::EncodingクラスのGetBytesからarray<Byte>^型の値を取得して、strcpyというのも。)

    (2)
    int::Parse
    int::TryParse
    Convert::ToInt32
    あたりを使って変換できます。

    もちろん、(1)の方法とかを使って、const char*型やconst wchar_t*型の値から、
    strtol,atoi,sscanf等ってのもありかもしれないけど、ムダが多いです。

    類似の問題の記事を見つけました。

    TITLE:Re: System::String を Char に変換する方法について - MSDNフォーラム
    URL:
    http://forums.microsoft.com/MSDN-JA/ShowPost.aspx?PostID=798561&SiteID=7

    sprintf()を使う方法ですが、皆さん優秀ですねぇ。

    今日受けたアドバイスは熟練者のテクニックであるとの記事も出てきました。

    ・・・今日は帰りますので、またあとでよろしくお願いします。

    2006年10月13日 10:43
  • char型配列に入れる例です。
    考えついただけ載せてみました。
    ただ、sprintfの方法は正攻法のやり方なのか確信できていないので載せていません。

    #include <cstring> // strcpy_s
    #include <cstdio>  // printf
    #include <clocale> // setlocal
    #include <cstdlib> // wcstombs_s
    #include <vcclr.h> // PtrToStringChars
    
    void sample1( System::String^ s )
    {
        char buff[ 256 ];
    
        System::IntPtr p
    = System::Runtime::InteropServices::Marshal::StringToHGlobalAnsi( s ); strcpy_s( buff, static_cast< const char* >( p.ToPointer() ) );
    System::Runtime::InteropServices::Marshal::FreeHGlobal( p ); printf( "sample1 : %s\n", buff ); } void sample2( System::String^ s ) { char buff[ 256 ]; array< unsigned char >^ a
    = System::Text::Encoding::GetEncoding( L"Shift_JIS" )->GetBytes( s ); pin_ptr< const unsigned char > p = &a[ 0 ]; strcpy_s( buff, static_cast<const char*>(static_cast<const void*>(p)) ); printf( "sample2 : %s\n", buff ); } void sample3( System::String^ s ) { char buff[ 256 ]; size_t ret = 0; // wchar_t wbuff[ 256 ]; pin_ptr< const wchar_t > p = PtrToStringChars( s ); // wcscpy_s( wbuff, p ); wcstombs_s( &ret, buff, p, ( wcslen( p ) + 1 ) * sizeof( wchar_t ) ); // wprintf( L"sample3 : %s\n", wbuff ); printf( "sample3 : %s\n", buff ); } void sample4( System::String^ s ) { char buff[ 256 ]; size_t ret = 0; array< wchar_t >^ a = s->ToCharArray(); pin_ptr< const wchar_t > p = &a[ 0 ]; wcstombs_s( &ret, buff, p, ( wcslen( p ) + 1 ) * sizeof( wchar_t ) ); printf( "sample4 : %s\n", buff ); } int main() { setlocale( LC_ALL, "Japanese" ); // wcstombs_sのため System::String^ s = L"あいうえおABC"; sample1( s ); sample2( s ); sample3( s ); sample4( s ); return 0; }
    2006年10月13日 11:15
  • 家に到着し、夕食を食べたところです。

    これだけ短時間にここまでプログラムが書けてしまうとは素晴らしい力ですね。

    見知らぬ関数や記述法も沢山あります。優れた情報提供を誠にありがとうございます。

    しっかり参考に致します。

     

    2006年10月13日 12:57
  • あ~よく考えたら、sample2,sample4はダメでした。
    配列が NULL文字で終端していないのでアクセスエラーになりますね。
    配列を拡張してNULL文字を付け足すか、strncpy_s等を使うしかないですね。

    訂正版)
    void sample2( System::String^ s )
    {
        char buff[ 256 ];
    
        array< unsigned char >^ a 
    = System::Text::Encoding::GetEncoding( L"Shift_JIS" )->GetBytes( s ); pin_ptr< const unsigned char > p = &a[ 0 ]; // strncpy_sはNULL文字まで付加してくれる(strncpyはつけないが) strncpy_s( buff,
    static_cast<const char*>( static_cast<const void*>( p ) ), a->Length ); printf( "sample2 : %s\n", buff ); }
    void sample4( System::String^ s )
    {
        char buff[ 256 ];
        size_t ret;
    
        array< wchar_t >^ a = s->ToCharArray();
        pin_ptr< const wchar_t > p = &a[ 0 ];
    
        // wcstombs_sはNULL文字まで付加してくれる
        wcstombs_s( &ret, buff, p, a->Length * sizeof( wchar_t ) );
    
        printf( "sample4 : %s\n", buff );
    }
    2006年10月13日 23:14
  • ありがとうございます。参考にして頑張ってみます。

     追伸:

    Stringから文字列への変換が正常にできました。

    ご教示ありがとうございました。

     

    2006年10月16日 0:32