2008-09-16 4 views
2

Хотя существует 100 способов решения проблемы преобразования, я сосредоточен на производительности.Использование C#, что является наиболее эффективным методом преобразования строки, содержащей двоичные данные, в массив байтов

Дать, что строка содержит только двоичные данные, что является самым быстрым методом с точки зрения производительности преобразования этой информации в байт [] (не char []) под C#?

Уточнение: это не данные ASCII, а скорее двоичные данные, находящиеся в строке.

+0

Строка содержит только двоичные данные? Что это значит? В нем есть только «1» и «0»? – 2008-09-16 13:47:12

ответ

3

Я не уверен, что ASCIIEncoding.GetBytes собирается это сделать, потому что он поддерживает только range 0x0000 to 0x007F.

Вы говорите, что строка содержит только байты. Но строка .NET представляет собой массив символов, а 1 char - 2 байта (поскольку .NET хранит строки как UTF16). Таким образом, вы можете иметь две ситуации для хранения байта 0x42 и 0x98:

  1. Строка была строка ANSI и содержит байты и преобразуется в строку Юникода, таким образом, байты будут 0x00 0x42 0x00 0x98. (Строка сохраняется как 0x0042 и 0x0098)
  2. Строка представляла собой только массив байтов, который вы приписывали или просто получали строку, и таким образом стали следующими байтами 0x42 0x98. (Строка сохраняется как 0x9842)

В первой ситуации на результат будет 0x42 и 0x3F (ascii для «B?»). Вторая ситуация привела бы к 0x3F (ascii для «?»). Это логично, потому что символы находятся за пределами допустимого диапазона ascii, и кодер не знает, что делать с этими значениями.

Так что мне интересно, почему это строка с байтами?

  • Возможно, он содержит байт, закодированный как строка (например, Base64)?
  • Возможно, вам стоит начать с массива символов или массива байтов?

Если у вас действительно есть ситуация 2, и вы хотите получить из нее байты, вы должны использовать вызов UnicodeEncoding.GetBytes. Потому что это вернет 0x42 и 0x98.

Если вы хотите перейти от массива символов к массиву байтов, самым быстрым способом будет Marshaling. Но это не очень приятно и использует двойную память.

public Byte[] ConvertToBytes(Char[] source) 
{ 
    Byte[] result = new Byte[source.Length * sizeof(Char)]; 
    IntPtr tempBuffer = Marshal.AllocHGlobal(result.Length); 
    try 
    { 
     Marshal.Copy(source, 0, tempBuffer, source.Length); 
     Marshal.Copy(tempBuffer, result, 0, result.Length); 
    } 
    finally 
    { 
     Marshal.FreeHGlobal(tempBuffer); 
    } 
    return result; 
} 
+0

@Davy Landman: Думаю, мы могли бы использовать более подробные сведения о его требованиях. – user7116 2008-09-16 14:49:46

0

Там нет нет такой вещи в виде строки ASCII в C#! Строки всегда содержат UTF-16. Не осознавая этого, возникает множество проблем. Тем не менее, упомянутые выше методы, потому что они рассматривают строку как кодировку UTF-16 и преобразуют символы в символы ASCII.

/EDIT в ответ на разъяснение: как бинарные данные попадали в строку? Строки не должны содержать двоичные данные (для этого используйте byte[]).

+0

Я думаю, что пользователь имеет странный формат файла со смешанным текстом и двоичными данными. – 2008-09-16 16:36:13

0

Если вы хотите перейти из строки двоичных данных, вы должны знать, какая кодировка используется для преобразования двоичных данных в строку, в первую очередь.В противном случае вы можете не получить правильные двоичные данные. Таким образом, наиболее эффективным способом является, вероятно, GetBytes() в подклассе кодирования (например, UTF8Encoding), но вы обязательно должны знать, какая кодировка.

Комментарий Кент Боогаарт по оригинальному вопросу суммирует его довольно хорошо. ;]