C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

ログ内検索
  • キーワードを複数指定する場合は 半角スペース で区切ってください。
  • 検索条件は、(AND)=[A かつ B] (OR)=[A または B] となっています。
  • [返信]をクリックすると返信ページへ移動します。
キーワード/ 検索条件 /
検索範囲/ 強調表示/ ON (自動リンクOFF)
結果表示件数/ 記事No検索/ ON
大文字と小文字を区別する

No.87146 の関連記事表示

<< 0 >>
■87146  Byte配列→文字列→Byte配列の方法策
□投稿者/ io -(2018/04/16(Mon) 13:54:46)

    分類:[.NET 全般] 

    現在困っていて教えてください

    あるByte配列をList of Tでリスト作成して、そのリストを使って色々しているのんですが

    Byte配列を文字列に変更し、一旦テキストへファイルへ保存
    読み込んで、またByte配列に戻したいんですが
    これができません

    現在Listは

    count0
    10
    20
    11
    15
    FF
    count1
    10
    .
    .
    とあります

    これを一旦文字列配列に直します
    01,10 20 11 15 FF
    02,10 20 ・・・・

    というのをテキストで作成し
    またreadalllineで string配列に戻し
    byteListへ戻したいんですが ここができないです

    流れとして
    @ Private recive As New List(Of Byte()) で リストを作成
    A ここに recive.Add(Byte配列)を入れていく
    Brecive(Index)をある分だけ、string変換
    Cstrをテキスト保存
    Dファイルからstring配列(Load_str)に読み込み
    Eload_strをまた新しいbyte配列へ変換
    Frecive.Add(New Byte)





    Dim load As String() = File.ReadAllLines("C\テスト\test.csv", enco)

    Dim bytedata As Byte()
    bytedata = New Byte() {}

    For i As Integer = 0 To load.Length - 1
    bytedata(i) = CByte(Convert.ToInt32(load(i), 16))
    Next

    コンバートすればいけるかな思いましたが
    文字列の終わりに、追加の解析できない文字がありました。エラーがでます

    そもそも、やり方が間違ってるのかしらべたんですが
    わからずこちらで、ご質問させていただきました。

    よろしくお願い致します。
親記事 /過去ログ149より / 関連記事表示
削除チェック/

■87147  Re[1]: Byte配列→文字列→Byte配列の方法策
□投稿者/ furu -(2018/04/16(Mon) 14:21:17)
    No87146 (io さん) に返信
    > bytedata(i) = CByte(Convert.ToInt32(load(i), 16))
    Byteを文字列にしたので
    1バイト→2文字だよね

    load(i)だと1文字分しかないような
記事No.87146 のレス /過去ログ149より / 関連記事表示
削除チェック/

■87148  Re[1]: Byte配列→文字列→Byte配列の方法策
□投稿者/ 魔界の仮面弁士 -(2018/04/16(Mon) 15:18:41)
    2018/04/16(Mon) 16:18:23 編集(投稿者)

    No87146 (io さん) に返信
    > あるByte配列をList of Tでリスト作成して、そのリストを使って色々しているのんですが
    文字列化する意図が分からなかったのですが、File.ReadAllBytes / File.WriteAllBytes を使って、
    テキストではなく、バイナリとして保持する…というわけにはいかないのですね?


    > Byte配列を文字列に変更し、一旦テキストへファイルへ保存
    Convert クラスの ToBase64String / FromBase64String メソッドでは駄目でしょうか?

    io さんがやろうとしている方法(いわゆる hexString)では、
    テキスト化に伴い、データ量が 2 倍(200%)に増加しますが、
    上記(BASE64)の場合は 4/3 倍(133%) で済みます。



    > @ Private recive As New List(Of Byte()) で リストを作成
    > A ここに recive.Add(Byte配列)を入れていく
    recive ではなく
    receive なのでは、という点はさておき。

    上記の変数宣言が、
     Private recive As New List(Of Byte) '(a)
    ではなく、
     Private recive As New List(Of Byte()) '(b)
    になっていますが、これは間違いないのですね?


    (a) の場合は、単一のバイナリを蓄えるもので、たとえば
     recive.AddRange(New Byte() { &H01, &H03, &H05, &H07 })
     recive.AddRange(New Byte() { &H09, &H0B, &H0D, &H0F, &H11, &H13 })
    などのように使うもの。この場合、recive.Count は 10 を返します。

    (b) の場合は、複数のバイナリを蓄えるもので、たとえば
     recive.Add(New Byte() { &H01, &H03, &H05, &H07 })
     recive.Add(New Byte() { &H09, &H0B, &H0D, &H0F, &H11, &H13 })
    などのように使うものですね。この場合、recive.Count は 2 を返し、
    recive(0).Length は 4 を返し、recive(1).Length は 6 を返します。



    > Brecive(Index)をある分だけ、string変換
    > Cstrをテキスト保存
    VB には「Str 関数」が存在するので、str という名の変数は避けた方が良いですよ。
    とりあえず、ここでいう recive(Index) が、上記 (b) を表すのであれば、
     Dim str1 As String = BitConverter.ToString(recive(0)).Replace("-", "")
     Dim str2 As String = BitConverter.ToString(recive(1)).Replace("-", "")
    とすることで、
     Dim str1 As String = "0103050709"
     Dim str2 As String = "0B0D0F1113"
    という結果を得ることが出来ます。
    (Replace しなかった場合には、2 文字ごとに "-" が入ります)


    > Dファイルからstring配列(Load_str)に読み込み
    Cの str との関係性が分かりませんが、これが
    > Dim load As String() = File.ReadAllLines("C\テスト\test.csv", enco)
    の部分ということでしょうか。

    だとすると、C:\テストではなく C\テストになっていますが、間違いないでしょうか。
    また、一括読み込みのための File.ReadAllText や ReadAllBytes を使わず、
    行単位読み込みの File.ReadAllLines を使っているのは意図的なものでしょうか。


    > Eload_strをまた新しいbyte配列へ変換
    元はバイナリであるはずの csv ファイルを、テキストデータとして文字列にデコードし、
    それを再度バイナリデータに、別の形式で再エンコードするという流れなのですか?
    回りくどい作業が行われているように思うのですが、
    本当にその手順は必要なものなのでしょうか。


    > Frecive.Add(New Byte)
    ここの説明が、先の説明と矛盾していますね。

    recive.Add(New Byte() {}) なら、Private recive As New List(Of Byte()) ですし、
    recive.Add(New Byte()) なら、Private recive As New List(Of Byte) のはず。


    > Dim load As String() = File.ReadAllLines("C\テスト\test.csv", enco)
    ちなみに File.ReadAllLines メソッドは、
    「改行が、レコードとレコードの間に配置されるタイプの CSV テキスト」と
    「改行が、各レコードの末尾に配置されるタイプの CSV テキスト」を
    区別できませんのでご注意ください。

    具体的には、CSV の中身が
    「あい,うえ{改行}かき,くけ」
    「あい,うえ{改行}かき,くけ{改行}」
    のいずれのファイルを読み取った場合も、load.Length が 2 になってしまうということです。

    そのため、この方法でファイルを読み取った場合は、元のファイルを
    完全再現させることができませんのでご注意ください。


    > For i As Integer = 0 To load.Length - 1
    > bytedata(i) = CByte(Convert.ToInt32(load(i), 16))
    > Next
    上記で i = 0 のときに、load(i) に格納されている文字列は何でしょうか?

    load(i) = "00" や load(i) = "FF" ならば、
    CByte まで成功します。

    load(i) = "0100" や load(i) = "0B0D0F11" ならば、
    ToInt32 は成功しますが、CByte の部分で失敗します。

    load(i) = "" や load(i) = "0B0D0F1113" だった場合、
    CByte はおろか、ToInt32 さえ失敗するでしょう。


    この部分だけを見れば、行単位で処理しようとするのではなく、
    hexString を 2 文字ずつ変換してやれば復元はできるでしょうが、
    bytedata() のインデックスは「バイト位置」で
    load() のインデックスは「行番号」なのですから、どちらにしても
    そもそもの変換ルールに問題があるように見えます。


    > そもそも、やり方が間違ってるのかしらべたんですが
    > わからずこちらで、ご質問させていただきました。

    やりたいことを、もう一度整理してみてください。

    数行の短い CSV ファイルを用意し、
    それぞれの変数に、どのような値が入ることを期待しているのかを
    再度考え直してみることをお奨めします。
記事No.87146 のレス /過去ログ149より / 関連記事表示
削除チェック/

■87149  Re[1]: Byte配列→文字列→Byte配列の方法策
□投稿者/ 魔界の仮面弁士 -(2018/04/16(Mon) 16:50:37)
    No87146 (io さん) に返信
    > これを一旦文字列配列に直します
    > 01,10 20 11 15 FF
    > 02,10 20 ・・・・
    最初はカンマ区切り、2 つ目以降はスペース区切りなのですね。

    最初の 2 文字 + カンマは、行番号を表すのでしょうか。
    (99 行目あるいは &HFF 行目を超えたときにどうなるのだろう…?)

    それとも、カンマでも空白でも許容する、ということなのでしょうか。


    > というのをテキストで作成し
    ここでいう「テキスト」が何を指しているのか読み取れませんでした。
    先ほどの「文字列」とは別のものなのですよね?


    > またreadalllineで string配列に戻し
    > byteListへ戻したいんですが ここができないです
    文字列とバイナリを行ったり来たりしていて、処理の流れが
    どうにも把握できていないのですが、ひとまず、こんな手順ではどうでしょうか。


    Dim src As String() = {"01,10 20 11 15 FF", "02,10 20"}
    Dim byteList As New List(Of Byte())

    byteList.Clear()
    For Each line As String In src
     '16進数文字列以外は捨てる
     line = New String(line.ToUpper().Where(Function(c) c Like "[0-9A-F]").ToArray())

     Using ms As New MemoryStream()
      '2文字ずつ切り出す
      For i As Integer = 0 To line.Length - 1 Step 2
       ms.WriteByte(Convert.ToByte(line.Substring(i, 2), 16))
      Next

      'byteList に詰める
      byteList.Add(ms.ToArray())
     End Using
    Next
記事No.87146 のレス /過去ログ149より / 関連記事表示
削除チェック/

■87150  Re[2]: Byte配列→文字列→Byte配列の方法策
□投稿者/ io -(2018/04/16(Mon) 17:47:12)
    2018/04/16(Mon) 17:53:11 編集(投稿者)
    2018/04/16(Mon) 17:53:09 編集(投稿者)

    詳しく説明して頂き 感謝いたします
    まだまだ勉強不足を痛感しています

    そもそも何をしたいか?
    も書いていないの意味がわかりませんよね。。

    Byte配列は、シリアル通信で入ってくるデータで
    受信すると、イベントチェンジプロシージャに入っていき
    そのたびにListに追加しています

    byte配列に対して、IDが振って

    Dictionaryで持っていて

    A,Byte配列1
    B,Byte配列2
    C,Byte配列3

    Aなら1というふうにプログラム上で書いていましたが
    ユーザー側が、Aにデータを追加したいとか
    出た案件で、簡単にユーザー側が使えるようにしたかったので
    txt,csvなどで管理するために
    わざわざテキストへ。。。と考えておりました

    しかし、自分がまだbyteに対して知識不足のため明らかに無駄な事をしているのが
    皆さんの教えでわかりました

    A,Byte配列1,Byte配列4
    B,Byte配列2
    C,Byte配列3

    4を簡単に追加できるようにプログラムでして
    外に保存し

    A,Byte配列1
    B,Byte配列2,Byte配列4
    C,Byte配列3

    とか

    A,Byte配列2
    B,Byte配列1,Byte配列4
    C,Byte配列3

    入れ替えたりをユーザー側で、できるような
    アプリを作成しようとしていました

    writebyteでやったほうが合理的ですかね?
記事No.87146 のレス /過去ログ149より / 関連記事表示
削除チェック/

■87151  Re[3]: Byte配列→文字列→Byte配列の方法策
□投稿者/ 魔界の仮面弁士 -(2018/04/16(Mon) 19:47:27)
    No87150 (io さん) に返信
    > Byte配列は、シリアル通信で入ってくるデータで

    であれば、元データはバイナリであって、文字列では無いのでは…。


    > 受信すると、イベントチェンジプロシージャに入っていき
    > そのたびにListに追加しています
    > byte配列に対して、IDが振って

    それが最初の質問の
    >> 01,10 20 11 15 FF
    >> 02,10 20 ・・・・
    における "01," や "02," なのですね?

    でもって、ID=01 と ID=02 は別々のデータであり、
    連結して一つにまとめるわけではない、と。


    > Dictionaryで持っていて
    > A,Byte配列1
    > B,Byte配列2
    > C,Byte配列3
    1 ではなく A になっている点が読み取れませんでしたが、
    ここでいう ID は連番というよりも、種別コードみたいなものなのかな…。


    > Aなら1というふうにプログラム上で書いていましたが
    > ユーザー側が、Aにデータを追加したいとか
    管理を Dictionary(Of 種別, List(Of Byte)) あたりにしておけば、
     dict(種別.A).AddRange( 追加したいバイナリ )
    とか、
     Dim bin As Byte() = dict(種別.B).ToArray()
    のような使い方ができそうです。


    > 出た案件で、簡単にユーザー側が使えるようにしたかったので
    > txt,csvなどで管理するために
    その csv がどういう使われ方をしているのか分からないのですが、
    今回問題になっているのはシリアル通信の部分ではなく、
    txt ファイルの内容をバイナリで読み取るところなのですね?


    ファイルから読み取られた
     Dim src As String = "10 20 11 15 FF"
    なデータを変換して、
     Dim dst As Byte() = { &H10, &H20, &H11, &H15, &HFF }
    にするのは、変換用に
     Function ToBinary( src As String) As Byte()
    なメソッドを一つ作ってやれば済む話ですし、実装例として
    No87149 とか No75726 とかを真似れば良いはず。


    あとは、先頭の ID 部分をどう管理するのかによって、
    コーディングが変わってくることになるかと。


    > 外に保存し
    「シリアル通信」でもデータを受け取り、「ファイル」でも受け取るのですか?

    どちらのデータがより優先させるのか、
    ファイルを開いている間に届いたシリアル通信のデータはどのように扱われるのか、
    そのファイルを「読み取る」だけでなく「書き込む」こともするのなら、排他制御の問題は、
    などなど、話が複雑化するような気がします…が、こちらはデータの流れを
    把握しているわけではないので、どうすべきかという点にまでは言及し難いです。
記事No.87146 のレス /過去ログ149より / 関連記事表示
削除チェック/

■87155  Re[4]: Byte配列→文字列→Byte配列の方法策
□投稿者/ io -(2018/04/17(Tue) 09:03:24)
    No87151 (魔界の仮面弁士 さん) に返信
    > ■No87150 (io さん) に返信

    > それが最初の質問の
    > >> 01,10 20 11 15 FF
    > >> 02,10 20 ・・・・
    > における "01," や "02," なのですね?
    >
    > でもって、ID=01 と ID=02 は別々のデータであり、
    > 連結して一つにまとめるわけではない、と。
    >
    その通りでございます
    ID=01とそれぞれ違う役割があるので
    ID=01に 0 20 11 15 FF Byte配列設定をしています

    >>C,Byte配列3
    > 1 ではなく A になっている点が読み取れませんでしたが、
    > ここでいう ID は連番というよりも、種別コードみたいなものなのかな…。

    わかりにくくてすいません、そのとおりです
    種別コードと思ってください。


    >>Aなら1というふうにプログラム上で書いていましたが
    >>ユーザー側が、Aにデータを追加したいとか
    > 管理を Dictionary(Of 種別, List(Of Byte)) あたりにしておけば、
    >  dict(種別.A).AddRange( 追加したいバイナリ )
    > とか、
    >  Dim bin As Byte() = dict(種別.B).ToArray()
    > のような使い方ができそうです。
    >

    これはやったことがないなので
    試してみます!

    > その csv がどういう使われ方をしているのか分からないのですが、
    > 今回問題になっているのはシリアル通信の部分ではなく、
    > txt ファイルの内容をバイナリで読み取るところなのですね?
    >
    簡単に言えば、システム作成側はByteなりどーいうものかなんとなくわかるのですが
    あくまでユーザーは一切わからない人達です

    ユーザーはID側だけ設定して
    それに対し、登録?みたいな感じで、Byteをシリアルで読み込んでます

    >
    > ファイルから読み取られた
    >  Dim src As String = "10 20 11 15 FF"
    > なデータを変換して、
    >  Dim dst As Byte() = { &H10, &H20, &H11, &H15, &HFF }
    > にするのは、変換用に
    >  Function ToBinary( src As String) As Byte()
    > なメソッドを一つ作ってやれば済む話ですし、実装例として
    > No87149 とか No75726 とかを真似れば良いはず。

    ありがとうございます
    変換は既にできています

    >
    >>外に保存し
    > 「シリアル通信」でもデータを受け取り、「ファイル」でも受け取るのですか?
    >
    > どちらのデータがより優先させるのか、
    > ファイルを開いている間に届いたシリアル通信のデータはどのように扱われるのか、
    > そのファイルを「読み取る」だけでなく「書き込む」こともするのなら、排他制御の問題は、
    > などなど、話が複雑化するような気がします…が、こちらはデータの流れを
    > 把握しているわけではないので、どうすべきかという点にまでは言及し難いです。

    簡単な話

    A,10 20 11 15 FF
    B,10 20 11 15 FF

    と Txtファイルに書き込ませて

    ABを逆にしたり
    A,10 20 11 15 FF,10 20 11 15 FF
    追加したり

    Byteを文字列に見せて
    コピペすればいいですよ的なものにしたかったです

    あとはプログラムが変換 dic登録をして
    システムへとつなげるみたいな感じで

    システム × ファイル ユーザー側
    システム = ファイル 作成側



    ユーザーはファイルだけいじるだけにしたかったのが目的となります






記事No.87146 のレス /過去ログ149より / 関連記事表示
削除チェック/



<< 0 >>

パスワード/

- Child Tree -