There is wonderful method which class String has in java called getBytes.
In C# it's also implemented in another class - Encoding, but unfortunately it returns array of unsigned bytes, which is a problem.
How is it possible to get an array of signed bytes in C# from a string?
Just use Encoding.GetBytes but then convert the byte[] to an sbyte[] by using something like Buffer.BlockCopy. However, I'd strongly encourage you to use the unsigned bytes instead - work round whatever problem you're having with them instead of moving to signed bytes, which were frankly a mistake in Java to start with. The reason there's no built-in way of converting a string to a signed byte array is because it's rarely something you really want to be doing.
If you can tell us a bit about why the unsigned bytes are causing you a problem, we may well be able to help you with that instead.
Related
This question is a bit similar to my previous one, where I asked a "cross-language" way to write and read integers between a Java and a C# program. Problem was the endianess.
Anyway, I'm facing a secondary problem. My goal is now to store and retrieve an array of unsigned bytes (values from 0 to 255) in a way that it can be processed by both Java and C#.
In C# it's easy, since unsigned byte[] exists:
BinaryWriterBigEndian writer = new BinaryWriterBigEndian(fs);
// ...
writer.Write(byteData, 0, byteData.Length);
BinaryWriterBigEndian is... well... a big-endian binary writer ;)
This way, the file will contain a sequence composed by, for example, the following values (in a big-endian representation):
[0][120][50][250][221]...
Now it's time to do the same thing under Java. Since unsigned byte[] does not exist here, the array is stored in memory as a (signed) int[] in order to have the possibility to represent values higher than 127.
How to write it as a sequence of unsigned byte values like C# does?
I tried with this:
ByteBuffer byteBuffer = ByteBuffer.allocate(4 * dataLength);
IntBuffer intBuffer = byteBuffer.asIntBuffer();
intBuffer.put(intData);
outputStream.write(byteBuffer.array());
Writing goes well, but C# is not able to read it in the proper way.
Since unsigned byte[] does not exist [...]
You don't care. Signed or unsigned, a byte is ultimately 8 bits. Just use a regular ByteBuffer and write your individual bytes in it.
In C# as well in Java, 1000 0000 (for instance) is exactly the same binary representation of a byte; the fact that in C# it can be treated as an unsigned value, and not in Java, is irrelevant as long as you don't do any arithmetic on the value.
When you need a readable representation of it and you'd like it to be unsigned, you can use (int) (theByte & 0xff) (you need the mask, otherwise casting will "carry" the sign bit).
Or, if you use Guava, you can use UnsignedBytes.toString().
In the .NET SerialPort class the ReadExisting() method returns a String instead of an array of bytes. This seems like an odd choice considering that RS232 is typically used to move 7 or 8 bit values, which may or may not be printable characters. Is there a reason for this choice?
Currently I end up using System.Text.Encoding.GetBytes(recvd_data) to convert the String to a byte array. Is there a more efficient method?
SerialPort has a Read overload that reads into the specified Byte[].
http://msdn.microsoft.com/en-us/library/ms143549(v=vs.100).aspx
I have used SerialPort extensively and the best way i've found to read a series of bytes is making multiple calls to ReadByte(). Yes, you read one byte at a time but i've found that keeping it simple has avoided problems.
At best, this method will save you from having to do a convert (since you'll read into a byte array).
I have an application that expects 5 bytes that is derived of a number. Right now I am using Uint32 which is 4 bytes. I been told to make a class that uses a byte and a Uint32. However, im not sure how to combine them since they are numbers.
I figured the best way may be to use a Uint64 and convert it down to 5 bytes. However, I am not sure how that can be done. I need to be able to convert it to 5 bytes and a separate function in the class to convert it back to a Uint64.
Does anyone have any ideas on the best way to do this?
Thank you
Use BitConverter.GetBytes and then just remove the three bytes you don't need.
To convert it back use BitConverter.ToUInt64 remembering that you'll have to first pad your byte array with three extra (zero) bytes.
Just watch out for endianness. You may need to reverse your array if the application you are sending these bytes to expects the opposite endianess. Also the endianess will dictate whether you need to add/remove bytes from the start or end of the array. (check BitConverter.IsLittleEndian)
I have an application converted from Python 2 (where strings are essentially lists of bytes) and I'm using a string as a convenient byte buffer.
I am rewriting some of this code in the Boo language (Python-like syntax, runs on .NET) and am finding that the strings have an intrinsic encoding type, such as ASCII, UTF-8, etc. Most of the information dealing with bytes refer to arrays of bytes, which are (apparently) fixed length, making them quite awkward to work with.
I can obviously get bytes from a string, but at the risk of expanding some characters into multiple bytes, or discarding/altering bytes above 127, etc. This is fine and I fully understand the reasons for this - but what would be handy for me is either (a) an encoding that guarantees no conversion or discarding of characters so that I can use a string as a convenient byte buffer, or (b) some sort of ByteString class that gives the convenience of the string class. (Ideally the latter as it seems less of a hack.) Do either of these already exist? (Or are trivial to implement?)
I am aware of System.IO.MemoryStream, but the prospect of creating one of those each time and then having to make a System.IO.StreamReader at the end just to get access to ReadToEnd() doesn't seem very efficient, and this is in performance-sensitive code.
(I hope nobody minds that I tagged this as C# as I felt the answers would likely apply there also, and that C# users might have a good idea of the possible solutions.)
EDIT: I've also just discovered System.Text.StringBuilder - again, is there such a thing for bytes?
Use the Latin-1 encoding as described in this answer. It maps values in the range 128-255 unchanged, useful when you want to roundtrip bytes to chars.
UPDATE
Or if you want to manipulate bytes directly, use List<byte>:
List<byte> result = ...
...
// Add a byte at the end
result.Add(b);
// Add a collection of bytes at the end
byte[] bytesToAppend = ...
result.AddRange(bytesToAppend);
// Insert a collection of bytes at any position
byte[] bytesToInsert = ...
int insertIndex = ...
result.InsertRange(insertIndex, bytesToInsert);
// Remove a range of bytes
result.RemoveRange(index, count);
... etc ...
I've also just discovered System.Text.StringBuilder - again, is there such a thing for bytes?
The StringBuilder class is needed because regular strings are immutable, and a List<byte> gives you everything you might expect from a "StringBuilder for bytes".
I would suggest that you use MemoryStream combined with the GetBuffer() operator to retrieve the end result. Strings are actually fixed length and immutable, and to add or replace one byte to a string requires you to copy the whole thing into a new string, which is quite slow. To avoid this you would need to use a StringBuilder which allocates memory and doubles the capacity when needed, but then you might just as well use MemoryStream instead which does a similar thing but on bytes.
Each element in the string is a char and are actually two bytes because .NET strings are always UTF-16 in memory, which means you will also be wasting memory if you decide to store only one byte in each element.
I need to create a structure or series of strings that are fixed lenght for a project I am working on. Currently it is written in COBOL and is a communication application. It sends a fixed length record via the web and recieves a fixed length record back. I would like to write it as a structure for simplicity, but so far the best thing I have found is a method that uses string.padright to put the string terminator in the correct place.
I could write a class that encapsulates this and returns a fixed length string, but I'm hoping to find a simple way to fill a structure and use it as a fixed length record.
edit--
The fixed length record is used as a parameter in a URL, so its http:\somewebsite.com\parseme?record="firstname lastname address city state zip". I'm pretty sure I won't have to worry about ascii to unicode conversions since it's in a url. It's a little larger than that and more information is passed than address, about 30 or 35 fields.
Add the MarshalAs tag to your structure. Here is an example:
<StructLayout (LayoutKind.Sequential, CharSet:=CharSet.Auto)> _
Public Structure OSVERSIONINFO
Public dwOSVersionInfoSize As Integer
Public dwMajorVersion As Integer
Public dwMinorVersion As Integer
Public dwBuildNumber As Integer
Public dwPlatformId As Integer
<MarshalAs (UnmanagedType.ByValTStr, SizeConst:=128)> _
Public szCSDVersion As String
End Structure
http://bytes.com/groups/net-vb/369711-defined-fixed-length-string-structure
You could use the VB6 compat FixedLengthString class, but it's pretty trivial to write your own.
If you need parsing and validation and all that fun stuff, you may want to take a look at FileHelpers which uses attributes to annotate and parse fixed length records.
FWIW, on anything relatively trivial (data processing, for instance) I'd probably just use a ToFixedLength() extension method that took care of padding or truncating as needed when writing out the records. For anything more complicated (like validation or parsing), I'd turn to FileHelpers.
byte[] arrayByte = new byte[35];
// Fill arrayByte with the other function
//Convert array of byte to string chain
string arrayStringConverr = Encoding.ASCII.GetString(arrayByte, 0, arrayByte.Length);
As an answer, you should be able to use char arrays of the correct size, without having to marshal.
Also, the difference between a class and a struct in .net is minimal. A struct cannot be null while a class can. Otherwise their use and capabilities are pretty much identical.
Finally, it sounds like you should be mindful of the size of the characters that are being sent. I'm assuming (I know, I know) that COBOL uses 8bit ASCII characters, while .net strings are going to use a UTF-16 encoded character set. This means that a 10 character string in COBOL is 10 bytes, but in .net, the same string is 20 bytes.