16 進数文字列の処理
ここのところお仕事過多な事もあって blog がちっとも更新出来ていません。。。
「 WebService から情報を取得するアプリケーションの作成」の 3 回目は手元で一生懸命原稿を書いているところです。今しばらくお待ちくださいませ><
で、あまりにも忙しいと何となく他の事をやりたくなるのが常でありまして。 ^^;
ちょっとした小ネタを。
- ネタ元: (Ito Blog)
上記記事では char から int への変換を計算で行っていますが、折角組み込みで Parse メソッドがあるのでそちらを使ってやる方法をご紹介します。
ついでにビット演算については BitArray (System.Collections) を利用して Bit 構造体なるものを作ってみました。 ^^;
Bit 構造体
# Equals とか GetHashCode とかの実装は面倒なので省略しています。
# まぁ、 GetHashCode については、実質 IntValue と同等な値なので、 "return IntValue.GetHashCode()" とかで良い気がします。 :p
# 演算についてはオーバーフローとか一切気にしてないので、このまま実運用とかで使うのは危険。。。
using System; using System.Collections; using System.Globalization; using System.Linq; using System.Text; public struct Bit { private BitArray _bitArray; #region int 値 public int IntValue { get; set; } #endregion #region インデクサ public bool this[int index] { get { return _bitArray[index]; } set { _bitArray[index] = value; RefreshIntValue(); } } #endregion #region コンストラクタ public Bit(string hexString) : this() { var intValue = Bit.HexStringToInt32(hexString); _bitArray = new BitArray(new[] { intValue }); IntValue = intValue; } public Bit(int intValue) : this() { _bitArray = new BitArray(new[] { intValue }); IntValue = intValue; } #endregion #region static メソッド public static int HexStringToInt32(string hexString) { return Int32.Parse(hexString, NumberStyles.HexNumber); } public static string Int32ToHexString(int intValue) { return intValue.ToString("X"); } #endregion #region 文字列化 public string ToHexString() { return Bit.Int32ToHexString(IntValue); } public string ToBitString() { return _bitArray.Cast<bool>() .Reverse() .SkipWhile(b => !b) .Aggregate( new StringBuilder(), (builder, b) => builder.Append(b ? 1 : 0) ) .ToString(); } #endregion #region int 値最新化 private void RefreshIntValue() { var round = 1; IntValue = 0; foreach (bool bit in _bitArray) { if (bit) { IntValue += round; } round *= 2; } } #endregion #region int との相互変換 public static implicit operator Bit(int intValue) { return new Bit(intValue); } public static implicit operator Int32(Bit bitValue) { return bitValue.IntValue; } #endregion #region string との相互変換 public static explicit operator Bit(string hexString) { return new Bit(hexString); } public static implicit operator String(Bit bitValue) { return bitValue.ToHexString(); } #endregion #region 演算子オーバーロード public static Bit operator +(Bit value, Bit other) { return new Bit(value.IntValue + other.IntValue); } public static Bit operator -(Bit value, Bit other) { return new Bit(value.IntValue - other.IntValue); } public static Bit operator *(Bit value, Bit other) { return new Bit(value.IntValue * other.IntValue); } public static Bit operator /(Bit value, Bit other) { return new Bit(value.IntValue / other.IntValue); } public static Bit operator %(Bit value, Bit other) { return new Bit(value.IntValue % other.IntValue); } public static bool operator ==(Bit value, Bit other) { return value.IntValue == other.IntValue; } public static bool operator !=(Bit value, Bit other) { return value.IntValue != other.IntValue; } #endregion }
使い方
// 16 進数文字列 → int var sampleString = "AF7"; var sampleInteger = Bit.HexStringToInt32(sampleString); Console.WriteLine("{0} -> {1}", sampleString, sampleInteger); Console.WriteLine(); // int → 16 進数文字列 var sample2Integer = 299; var sample2String = Bit.Int32ToHexString(sample2Integer); Console.WriteLine("{0} -> {1}", sample2Integer, sample2String); Console.WriteLine(); // Bit 構造体の利用 // 16 進数文字列 → Bit 構造体 var sample3String = "3B9"; var sample3Bit = (Bit)sample3String; // 明示的な型変換が可能 // int / 16 進数文字列 / 2 進数文字列として取得 var sample3Integer = sample3Bit.IntValue; var sample3HexString = sample3Bit.ToHexString(); var sample3BitString = sample3Bit.ToBitString(); Console.WriteLine("[int] {0}", sample3Integer); Console.WriteLine("[16] {0}", sample3HexString); Console.WriteLine("[2] {0}", sample3BitString); Console.WriteLine(); // int → Bit 構造体 Bit sample4Bit = 189; // 暗黙的な型変換が可能 int sample4Integer = sample4Bit; // Bit 構造体 → int も暗黙的な型変換が可能 Console.WriteLine("[Bit] {0}", sample4Bit.ToHexString()); Console.WriteLine("[int] {0}", sample4Integer); Console.WriteLine(); // 特定箇所のビットを bool 値で取得 Bit sample5Bit = 288; var sample5ChoiceIndex = 4; var sample5ChoiceBit = sample5Bit[sample5ChoiceIndex]; // インデックスアクセスが可能 Console.WriteLine("{0} [{1}] -> {2}", sample5Bit.ToHexString(), sample5ChoiceIndex, sample5ChoiceBit); Console.WriteLine("<{0}>", sample5Bit.ToBitString()); Console.WriteLine(); // 特定箇所のビットを更新 var sample6Bit = (Bit)"BDF37"; var sample6OriginalHexString = sample6Bit.ToHexString(); var sample6OriginalBitString = sample6Bit.ToBitString(); var sample6OriginalInteger = sample6Bit.IntValue; var updateIndex = 3; var updateValue = true; sample6Bit[updateIndex] = updateValue; // インデックスアクセスが可能 Console.WriteLine("{0} >> [{1}, {2}] -> {3}", sample6OriginalHexString, updateIndex, updateValue, sample6Bit.ToHexString()); Console.WriteLine("{0} >> [{1}, {2}] -> {3}", sample6OriginalInteger, updateIndex, updateValue, sample6Bit.IntValue); Console.WriteLine("before: <{0}>", sample6OriginalBitString); Console.WriteLine("after : <{0}>", sample6Bit.ToBitString()); Console.WriteLine(); // 演算 Bit sample7Bit = 27; Bit sample8Bit = (Bit)"C"; var plus = sample7Bit + sample8Bit; var minus = sample7Bit - sample8Bit; var times = sample7Bit * sample8Bit; var divide = sample7Bit / sample8Bit; var mod = sample7Bit % sample8Bit; Console.WriteLine("Hex: {0}, {1}", sample7Bit.ToHexString(), sample8Bit.ToHexString()); Console.WriteLine("Int: {0}, {1}", sample7Bit.IntValue, sample8Bit.IntValue); Console.WriteLine("+ >> Hex: {0} , Int: {1}", plus.ToHexString(), plus.IntValue); Console.WriteLine("- >> Hex: {0} , Int: {1}", minus.ToHexString(), minus.IntValue); Console.WriteLine("* >> Hex: {0} , Int: {1}", times.ToHexString(), times.IntValue); Console.WriteLine("/ >> Hex: {0} , Int: {1}", divide.ToHexString(), divide.IntValue); Console.WriteLine("% >> Hex: {0} , Int: {1}", mod.ToHexString(), mod.IntValue);
- 出力結果
AF7 -> 2807 299 -> 12B [int] 953 [16] 3B9 [2] 1110111001 [Bit] BD [int] 189 120 [4] -> False <100100000> BDF37 >> [3, True] -> BDF3F 778039 >> [3, True] -> 778047 before: <10111101111100110111> after : <10111101111100111111> Hex: 1B, C Int: 27, 12 + >> Hex: 27 , Int: 39 - >> Hex: F , Int: 15 * >> Hex: 144 , Int: 324 / >> Hex: 2 , Int: 2 % >> Hex: 3 , Int: 3