1

char a[]のような 16 進文字があります。

"315c4eeaa8b5f8aaf9174145bf43e1784b8fa00dc71d885a804e5ee9fa40b16349c146fb778cdf2d3aff021dfff5b403b510d0d0455468aeb98622b137dae857553ccd8883a7bc37520e06e515d22c954eba5025b8cc57ee59418ce7dc6bc41556bdb36bbca3e8774301fbcaa3b83b220809560987815f65286764703de0f3d524400a19b159610b11ef3e"

次のように、各16進数に対応する文字に変換したい:

68656c6c6f = hello

に格納してからchar b[]、逆の操作を行います

コードのブロックは必要ありません。説明と、使用されたライブラリとその使用方法が必要です。

ありがとう

4

6 に答える 6

2

16 進文字列を文字列に変換するには、 を使用しstd::substrて 16 進文字列の次の 2 文字を取得し、 を使用std::stoiして部分文字列を整数に変換します。これは、 に追加された文字にキャストできますstd::stringstd::stoi関数は C++11 のみであり、それがない場合は、eg を使用できますstd::strtol

反対に、入力文字列の各文字をループし、それを整数にキャストし、std::ostringstream前にマニピュレーターを付けて2 桁0 接頭辞付き 16 進数として表示します。出力文字列に追加します。

std::string::c_str必要に応じて古いスタイルの Ccharポインターを取得するために使用します。

外部ライブラリはなく、C++ 標準ライブラリのみを使用します。

于 2012-11-12T13:06:07.897 に答える
2

あなたがASCIIコードについて話していると仮定します。さて、最初のステップは のサイズを見つけることですb。すべての文字が 2 桁の 16 進数であると仮定すると (たとえば、atabは になります09)、のサイズbは単純にstrlen(a) / 2 + 1です。

それが完了したらa、2 x 2 の文字を調べて、それらを整数値に変換し、文字列として保存する必要があります。あなたが持っている式として書かれています:

b[i] = (to_digit(a[2*i]) << 4) + to_digit(a[2*i+1]))

whereはおよびまたはにto_digit(x)変換'0'-'9'されます。0-9'a'-'z''A'-'Z'10-15

以下の文字0x10が 1 文字のみで表示されている場合 (私が考えることができる唯一の文字は であり、 のインデックスとしてtab使用する代わりに、ループ内にa を保持する必要があります。後者の場合、.2*ianext_indexa[next_index] < '8'b[i] = to_digit(a[next_index])

この操作の逆は非常に似ています。各文字b[i]は次のように記述されます。

a[2*i] = to_char(b[i] >> 4)
a[2*i+1] = to_char(b[i] & 0xf)

to_charの反対はどこですかto_digit

于 2012-11-12T13:09:23.427 に答える
1

前方:

  1. 入力から 2 つの 16 進文字を読み取ります。
  2. int (0..255) に変換します。(ヒント: sscanf は一方向です)
  3. int を出力 char 配列に追加します
  4. 文字がなくなるまで、1 ~ 3 を繰り返します。
  5. 配列をヌル終了する

逆行する:

  1. 配列から単一の文字を読み取る
  2. 2 つの 16 進数文字に変換します (ヒント: sprintf は一方向です)。
  3. (2) のバッファを最終的な出力文字列バッファに連結します。
  4. 文字がなくなるまで、1 ~ 3 を繰り返します。

言及するのをほとんど忘れていました。stdio.h と通常の C ランタイムのみが必要sscanfですsprintf。あるいは、変換を大幅に高速化する一対の変換テーブルを作成することもできます。

于 2012-11-12T13:09:42.053 に答える
0

hex16 進数との間の変換は、次のようにを使用して行うことができます。

cout << hex << x;
cin >> hex >> x;

の適切な定義x、例えばint x

これは、文字列ストリームでも機能するはずです。

于 2012-11-12T13:11:37.493 に答える
0

このトリックを実行するための簡単なコードを次に示します。

unsigned int hex_digit_value(char c)
{
    if ('0' <= c && c <= '9') { return c - '0'; }
    if ('a' <= c && c <= 'f') { return c + 10 - 'a'; }
    if ('A' <= c && c <= 'F') { return c + 10 - 'A'; }
    return -1;
}

std::string dehexify(std::string const & s)
{
    std::string result(s.size() / 2);

    for (std::size_t i = 0; i != s.size(); ++i)
    {
        result[i] = hex_digit_value(s[2 * i]) * 16
                  + hex_digit_value(s[2 * i + 1]);
    }

    return result;
}

使用法:

char const a[] = "12AB";

std::string s = dehexify(a);

ノート:

  • 適切な実装では、入力文字列の長さが偶数であり、各桁が実際に有効な 16 進数であることのチェックが追加されます。

  • Dehexifying は ASCII とは何の関係もありません。16 進化されたニブルのシーケンスをバイトのシーケンスに変換するだけです。私std::stringは便利な「バイトのコンテナ」として使用しているだけで、まさにそれです。

  • SOには、逆の方法を示す数十の回答があります。「hexify」を検索するだけです。

于 2012-11-12T13:32:27.240 に答える
0

各 16 進数は 4 ビットに対応します。これは、4 ビットには 16 の可能なビット パターンがあるためです (また、16 の可能な 16 進数があり、それぞれが一意の 4 ビット パターンを表します)。

つまり、16 進数 2 桁が 8 ビットに相当します。

また、最近のほとんどのコンピュータ (一部の Texas Instruments デジタル シグナル プロセッサは例外です) では、C++charは 8 ビットです。

これは、各 C++charが 2 桁の 16 進数で表されることを意味します。

したがって、一度に 2 つの 16 進数を読み取り、intたとえば を使用してistringstream変換し、それを に変換して、各値を にchar追加します。charstd::string

もう一方の方向は正反対ですが、ひねりがあります。

はほとんどのシステムで署名されているため、その値を 16 進数に再度char変換する前に に変換する必要があります。unsigned char

于 2012-11-12T13:04:12.723 に答える