I am writing a winform to convert written text into Unicode numbers and UTF8 numbers. This bit is working well
//------------------------------------------------------------------------
// Convert to UTF8
// The return will be either 1 byte, 2 bytes or 3 bytes.
//-----------------------------------------------------------------------
UTF8Encoding utf8 = new UTF8Encoding();
StringBuilder builder = new StringBuilder();
string utext = rchtxbx_text.Text;
// do one char at a time
for (int text_index = 0; text_index < utext.Length; text_index++)
{
byte[] encodedBytes = utf8.GetBytes(utext.Substring(text_index, 1));
for (int index = 0; index < encodedBytes.Length; index++)
{
builder.AppendFormat("{0}", Convert.ToString(encodedBytes[index], 16));
}
builder.Append(" ");
}
rchtxtbx_UTF8.SelectionFont = new System.Drawing.Font("San Serif", 20);
rchtxtbx_UTF8.AppendText(builder.ToString() + "\r");
As an example the characters 乘义ש give me e4b998 e4b989 d7a9, note I have a mix LtoR and RtoL text. Now if the user inputs the number e4b998 I want to show them it is 乘, in Unicode 4E58
I have tried a few things and the closest I got, but still far away, is
Encoding utf8 = Encoding.UTF8;
rchtxbx_text.Text = Encoding.ASCII.GetString(utf8.GetBytes(e4b998));
What do I need to do to input e4b998 and write 乘 to a textbox?
Something like this:
Split source into 2-character chunks: "e4b998" -> {"e4", "b9", "98"}
Convert chunks into bytes
Encode bytes into the final string
Implementation:
string source = "e4b998";
string result = Encoding.UTF8.GetString(Enumerable
.Range(0, source.Length / 2)
.Select(i => Convert.ToByte(source.Substring(i * 2, 2), 16))
.ToArray());
If you have an int as source:
string s_unicode2 = System.Text.Encoding.UTF8.GetString(utf8.GetBytes(e4b998));
Related
I read a file as binary, convert to hex string, convert back to binary, and write to a new file.
I expect a duplicate, but get a corrupted file.
I have been trying different ways to convert the binary into the hex string but can't seem to retain the entire file.
byte[] binary1 = File.ReadAllBytes(#"....Input.jpg");
string hexString = "";
int counter1 = 0;
foreach (byte b in binary1)
{
counter1++;
hexString += (Convert.ToString(b, 16));
}
List<byte> bytelist = new List<byte>();
int counter2 = 0;
for (int i = 0; i < hexString.Length/2; i++)
{
counter2++;
string ch = hexString.Substring(i*2,2);
bytelist.Add(Convert.ToByte(ch, 16));
}
byte[] binary2 = bytelist.ToArray();
File.WriteAllBytes(#"....Output.jpg", binary2);
Counter 1 and counter 2 should be the same count, but counter 2 is always about 10% smaller.
I want to get a duplicate file output that I could have transferred around via that string value.
Converting byte 10 will give a single char, and not 2 characters. Your convert back method (logically) build on 2 chars per byte.
this case works
byte[] binary1 = new byte[] { 100 }; // convert will result in "64"
and this case fails
byte[] binary1 = new byte[] { 10 }; // convert will result in "a"
I quick fixed your code, by padding with a "0" in case of a single char.
so working code:
byte[] binary1 = new byte[] { 100 };
string hexString = "";
int counter1 = 0;
foreach (byte b in binary1)
{
counter1++;
var s = (Convert.ToString(b, 16));
// new
if (s.Length < 2)
{
hexString += "0";
}
// end new
hexString += s;
}
List<byte> bytelist = new List<byte>();
int counter2 = 0;
for (int i = 0; i < hexString.Length / 2; i++)
{
counter2++;
string ch = hexString.Substring(i * 2, 2);
var item = Convert.ToByte(ch, 16);
bytelist.Add(item);
}
byte[] binary2 = bytelist.ToArray();
Please note, your code could use some refactoring, e.g. don't string concat in a loop and maybe check the Single Responsibility Principle.
Update, got it fixed, but there are better solutions here: How do you convert a byte array to a hexadecimal string, and vice versa?
I have an array of integer 1s and 0s (possibly need to get converted to byte type?). I have used an online ASCII to binary generator to get the equivalent binary of this 6 digit letter sequence:
abcdef should equal 011000010110001001100011011001000110010101100110 in binary. So in c#, my array is [0,1,1,0,0,0,0...], built by:
int[] innerArr = new int[48];
for (int i = 0; i < 48); i++) {
int innerIsWhite = color.val[0] > 200 ? 0 : 1;
innerArr[i] = innerIsWhite;
}
I want to take this array, and convert it into abcdef (and be able to do the opposite).
How do I do this? Is there a better way to be storing these ones and zeros.
Try using Linq and Convert:
source = "abcdef";
// 011000010110001001100011011001000110010101100110
string encoded = string.Concat(source
.Select(c => Convert.ToString(c, 2).PadLeft(8, '0')));
// If we want an array
byte[] encodedArray = encoded
.Select(c => (byte) (c - '0'))
.ToArray();
// string from array
string encodedFromArray = string.Concat(encodedArray);
// abcdef
string decoded = string.Concat(Enumerable
.Range(0, encoded.Length / 8)
.Select(i => (char) Convert.ToByte(encoded.Substring(i * 8, 8), 2)));
If your input is a bit string, then you can use a method like below to convert that into character string
public static string GetStringFromAsciiBitString(string bitString) {
var asciiiByteData = new byte[bitString.Length / 8];
for (int i = 0, j = 0; i < asciiiByteData.Length; ++i, j+= 8)
asciiiByteData[i] = Convert.ToByte(bitString.Substring(j, 8), 2);
return Encoding.ASCII.GetString(asciiiByteData);
}
The above code simply uses the Convert.ToByte method asking it to do a base-2 string to byte conversion. Then using Encoding.ASCII.GetString, you get the string representation from the byte array
In my code, I presume your bit string is clean (multiple of 8 and with only 0s and 1s), in production grade code you will have to sanitize your input.
I have a unicode string like this:
0030003100320033
Which should turn into 0123.
This is a simple case of 0123 string, but there are some string and unicode chars as well. How can I turn this type of unicode hex string to string in C#?
For normal US charset, first part is always 00, so 0031 is "1" in ASCII, 0032 is "2" and so on.
When its actual unicode char, like Arabic and Chinese, first part is not 00, for instance for Arabic its 06XX, like 0663.
I need to be able to turn this type of Hex string into C# decimal string.
There are several encodings that can represent Unicode, of which UTF-8 is today's de facto standard. However, your example is actually a string representation of UTF-16 using the big-endian byte order. You can convert your hex string back into bytes, then use Encoding.BigEndianUnicode to decode this:
public static void Main()
{
var bytes = StringToByteArray("0030003100320033");
var decoded = System.Text.Encoding.BigEndianUnicode.GetString(bytes);
Console.WriteLine(decoded); // gives "0123"
}
// https://stackoverflow.com/a/311179/1149773
public static byte[] StringToByteArray(string hex)
{
byte[] bytes = new byte[hex.Length / 2];
for (int i = 0; i < hex.Length; i += 2)
bytes[i / 2] = Convert.ToByte(hex.Substring(i, 2), 16);
return bytes;
}
Since Char in .NET represents a UTF-16 code unit, this answer should give identical results to Slai's, including for surrogate pairs.
Shorter less efficient alternative:
Regex.Replace("0030003100320033", "....", m => (char)Convert.ToInt32(m + "", 16) + "");
You should try this solution
public static void Main()
{
string hexString = "0030003100320033"; //Hexa pair numeric values
//string hexStrWithDash = "00-30-00-31-00-32-00-33"; //Hexa pair numeric values separated by dashed. This occurs using BitConverter.ToString()
byte[] data = ParseHex(hexString);
string result = System.Text.Encoding.BigEndianUnicode.GetString(data);
Console.Write("Data: {0}", result);
}
public static byte[] ParseHex(string hexString)
{
hexString = hexString.Replace("-", "");
byte[] output = new byte[hexString.Length / 2];
for (int i = 0; i < output.Length; i++)
{
output[i] = Convert.ToByte(hexString.Substring(i * 2, 2), 16);
}
return output;
}
I have a byte array:
newMsg.DATA = new byte[64];
How can I convert it into binary value and then write it in text file with comma separation. Comma should be in between binary values not bytes.....
like 1,1,1,0,0,0,1,1,1,1,1,0,0,0,0,0.......
Here is an example that uses LINQ:
byte[] arr = new byte[] { 11, 55, 255, 188, 99, 22, 31, 43, 25, 122 };
string[] result = arr.Select(x => string.Join(",", Convert.ToString(x, 2)
.PadLeft(8, '0').ToCharArray())).ToArray();
System.IO.File.WriteAllLines(#"D:\myFile.txt", result);
Every number in byte[] arr is converted to a binary number with Convert.ToString(x, 2) and the comma "," is added between binary values with string.Join(",",...). At the end you can write all the elements in result to a text file by using System.IO.File.WriteAllLines.
The example above gives you this kind of output in a txt file:
0,0,0,0,1,0,1,1
0,0,1,1,0,1,1,1
1,1,1,1,1,1,1,1
...
Explanation of Convert.ToString(value, baseValue):
The first parameter value represents the number you want to convert to a string
and the second parameter baseValue represents which type of conversion you want to perform.
Posible baseValues are : 2,8,10 and 16.
BaseValue = 2 - represents a conversion to a binary number representation.
BaseValue = 8 - represents a conversion to a octal number representation.
BaseValue = 10 - represents a conversion to a decimal number representation.
BaseValue = 16 - represents a conversion to a hexadecimal number representation.
I think this will Help you c# provides inbuilt functionality to do so
with help of Convert.ToString(byte[],base); here base could be[2(binary),8(octal),16(HexaDecimal)]
byte[] data = new byte[64];
// 2nd parameter 2 is Base e.g.(binary)
string a = Convert.ToString(data[data.Length], 2);
StringBuilder sb = new StringBuilder();
foreach(char ch in a.ToCharArray())
{
sb.Append(ch+",");
}
// This is to remove last extra ,
string ans = sb.ToString().Remove(sb.Length - 1, 1);
This should get you going:
var bytes = new byte[] { 128, 255, 2 };
var stringBuilder = new StringBuilder();
for (var index = 0; index < bytes.Length; index++)
{
var binary = Convert.ToString(bytes[index], 2).PadLeft(8, '0');
var str = string.Join(",", binary.ToCharArray());
stringBuilder.Append(str);
if (index != bytes.Length -1) stringBuilder.Append(",");
}
Console.WriteLine(stringBuilder);
I have a random integer value which I need to represent in String as a Byte array. For example:
int value = 32;
String strValue = getStringByteArray(value);
Console.WriteLine(strValue); // should write: " \0\0\0"
If value = 11 then getStringByteArray(value) shuld return "\v\0\0\0".
If value = 13 then getStringByteArray(value) shuld return "\r\0\0\0".
And so on.
Any idea on how to implement the method getStringByteArray(int value) in C#?
UPDATE
This is the code that receives the data from the C# NamedPipe Server:
bool CFilePipe::ReadString(int m_handle, string &value)
{
//--- check for data
if(WaitForRead(sizeof(int)))
{
ResetLastError();
int size=FileReadInteger(m_handle);
if(GetLastError()==0)
{
//--- check for data
if(WaitForRead(size))
{
value=FileReadString(m_handle,size);
return(size==StringLen(value));
}
}
}
//--- failure
return(false);
}
Don't take this approach at all. You should be writing to a binary stream of some description - and write the binary data for the length of the packet/message, followed by the message itself. For example:
BinaryWriter writer = new BinaryWriter(stream);
byte[] data = Encoding.UTF8.GetBytes(text);
writer.Write(data.Length);
writer.Write(data);
Then at the other end, you'd use:
BinaryReader reader = new BinaryReader(stream);
int length = reader.ReadInt32();
byte[] data = reader.ReadBytes(length);
string text = Encoding.UTF8.GetString(data);
No need to treat binary data as text at all.
Well. First of all you should get bytes from integer. You can do it with BitConverter:
var bytes = BitConverter.GetBytes(value);
Next, here is three variants. First - if you want to get result in binary format. Just take all your bytes and write as it is:
var str = string.Concat(bytes.Select(b => Convert.ToString(b, 2)));
Second variant. If you want convert your byte array to hexadecimal string:
var hex = BitConverter.ToString(array).Replace("-","");
Third variant. Your representation ("\v\0\0\0") - it is simple converting byte to char. Use this:
var s = bytes.Aggregate(string.Empty, (current, t) => current + Convert.ToChar(t));
This should help with that.
class Program
{
static void Main(string[] args)
{
Random rand = new Random();
int number = rand.Next(1, 1000);
byte[] intBytes = BitConverter.GetBytes(number);
string answer = "";
for (int i = 0; i < intBytes.Length; i++)
{
answer += intBytes[i] + #"\";
}
Console.WriteLine(answer);
Console.WriteLine(number);
Console.ReadKey();
}
}
Obviously, you should implement two steps to achieve the goal:
Extract bytes from the integer in the appropriate order (little-endian or big-endian, it's up to you to decide), using bit arithmetics.
Merge extracted bytes into string using the format you need.
Possible implementation:
using System;
using System.Text;
public class Test
{
public static void Main()
{
Int32 value = 5152;
byte[] bytes = new byte[4];
for (int i = 0; i < 4; i++)
{
bytes[i] = (byte)((value >> i * 8) & 0xFF);
}
StringBuilder result = new StringBuilder();
for (int i = 0; i < 4; i++)
{
result.Append("\\" + bytes[i].ToString("X2"));
}
Console.WriteLine(result);
}
}
Ideone snippet: http://ideone.com/wLloo1
I think you are saying that you want to convert each byte into a character literal, using escape sequences for the non printable characters.
After converting the integer to 4 bytes, cast to char. Then use Char.IsControl() to identify the non-printing characters. Use the printable char directly, and use a lookup table to find the corresponding escape sequence for each non-printable char.