Ich bin ziemlich neu in C #. Ich konvertiere etwas von VB in C #. Probleme mit der Syntax dieser Anweisung haben:
if ((searchResult.Properties["user"].Count > 0))
{
profile.User = System.Text.Encoding.UTF8.GetString(searchResult.Properties["user"][0]);
}
Ich sehe dann die folgenden Fehler:
Argument 1: Konvertierung von 'Objekt' nach 'Byte []' nicht möglich
Die beste überladene Methode für 'System.Text.Encoding.GetString (byte [])' enthält einige ungültige Argumente
Ich habe versucht, den Code basierend auf this post zu korrigieren, aber immer noch keinen Erfolg
string User = Encoding.UTF8.GetString("user", 0);
Irgendwelche Vorschläge?
Wenn Sie bereits über ein Byte-Array verfügen, müssen Sie wissen, welche Art von Codierung verwendet wurde, um es in dieses Byte-Array aufzunehmen.
Wenn das Byte-Array beispielsweise so erstellt wurde:
byte[] bytes = Encoding.ASCII.GetBytes(someString);
Sie müssen es wieder in eine Zeichenfolge umwandeln:
string someString = Encoding.ASCII.GetString(bytes);
Wenn Sie in dem von Ihnen geerbten Code die zum Erstellen des Bytearrays verwendete Codierung finden können, sollten Sie festgelegt werden.
Fügen Sie zunächst den System.Text
-Namespace hinzu
using System.Text;
Dann benutze diesen Code
string input = "some text";
byte[] array = Encoding.ASCII.GetBytes(input);
Hoffe, es zu beheben!
Sie können auch eine Extension-Methode verwenden, um eine Methode zum string
-Typ hinzuzufügen:
static class Helper
{
public static byte[] ToByteArray(this string str)
{
return System.Text.Encoding.ASCII.GetBytes(str);
}
}
Und benutze es wie folgt:
string foo = "bla bla";
byte[] result = foo.ToByteArray();
static byte[] GetBytes(string str)
{
byte[] bytes = new byte[str.Length * sizeof(char)];
System.Buffer.BlockCopy(str.ToCharArray(), 0, bytes, 0, bytes.Length);
return bytes;
}
static string GetString(byte[] bytes)
{
char[] chars = new char[bytes.Length / sizeof(char)];
System.Buffer.BlockCopy(bytes, 0, chars, 0, bytes.Length);
return new string(chars);
}
var result = System.Text.Encoding.Unicode.GetBytes(text);
benutze das
byte[] myByte= System.Text.ASCIIEncoding.Default.GetBytes(myString);
Der folgende Ansatz funktioniert nur, wenn die Zeichen 1 Byte sind. (Der Standard-Unicode funktioniert nicht, da er aus 2 Byte besteht.)
public static byte[] ToByteArray(string value)
{
char[] charArr = value.ToCharArray();
byte[] bytes = new byte[charArr.Length];
for (int i = 0; i < charArr.Length; i++)
{
byte current = Convert.ToByte(charArr[i]);
bytes[i] = current;
}
return bytes;
}
Einfach halten
Eine Verbesserung der Bearbeitung von JustinStolle (Eran Yogevs Verwendung von BlockCopy).
Die vorgeschlagene Lösung ist in der Tat schneller als die Verwendung von Encoding . Das Problem ist, dass sie nicht für das Codieren von Byte-Arrays mit ungleichmäßiger Länge arbeitet length by 1 hinterlässt bei der Decodierung von string ein nachfolgendes Byte.
Für mich bestand die Notwendigkeit, als ich von DataTable
in JSON
..__ codieren wollte. Ich suchte nach einer Möglichkeit, binäre Felder in Strings zu codieren und von String zurück nach byte[]
zu decodieren.
Ich habe daher zwei Klassen erstellt - eine, die die obige Lösung umschließt (wenn aus Strings codiert wird, ist dies in Ordnung, da die Längen immer gerade sind) und eine andere, die byte[]
-Codierung behandelt.
Ich habe das Problem der ungleichmäßigen Länge durch Hinzufügen eines einzelnen Zeichens gelöst, das angibt, ob die ursprüngliche Länge des binären Arrays ungerade ('1') oder gerade ('0') war.
Wie folgt:
public static class StringEncoder
{
static byte[] EncodeToBytes(string str)
{
byte[] bytes = new byte[str.Length * sizeof(char)];
System.Buffer.BlockCopy(str.ToCharArray(), 0, bytes, 0, bytes.Length);
return bytes;
}
static string DecodeToString(byte[] bytes)
{
char[] chars = new char[bytes.Length / sizeof(char)];
System.Buffer.BlockCopy(bytes, 0, chars, 0, bytes.Length);
return new string(chars);
}
}
public static class BytesEncoder
{
public static string EncodeToString(byte[] bytes)
{
bool even = (bytes.Length % 2 == 0);
char[] chars = new char[1 + bytes.Length / sizeof(char) + (even ? 0 : 1)];
chars[0] = (even ? '0' : '1');
System.Buffer.BlockCopy(bytes, 0, chars, 2, bytes.Length);
return new string(chars);
}
public static byte[] DecodeToBytes(string str)
{
bool even = str[0] == '0';
byte[] bytes = new byte[(str.Length - 1) * sizeof(char) + (even ? 0 : -1)];
char[] chars = str.ToCharArray();
System.Buffer.BlockCopy(chars, 2, bytes, 0, bytes.Length);
return bytes;
}
}
Hat jemand einen Grund, warum das nicht zu tun?
mystring.Select(Convert.ToByte).ToArray()
Wenn das Ergebnis von 'searchResult.Properties ["user"] [0]' eine Zeichenfolge ist:
if ( ( searchResult.Properties [ "user" ].Count > 0 ) ) {
profile.User = System.Text.Encoding.UTF8.GetString ( searchResult.Properties [ "user" ] [ 0 ].ToCharArray ().Select ( character => ( byte ) character ).ToArray () );
}
Der entscheidende Punkt ist, dass das Konvertieren eines Strings in ein Byte [] mit LINQ erfolgen kann:
.ToCharArray ().Select ( character => ( byte ) character ).ToArray () )
Und das Gegenteil:
.Select ( character => ( char ) character ).ToArray () )
Diese Frage wurde ausreichend oft genug beantwortet, aber mit C # 7.2 und der Einführung des Typs Span gibt es einen schnelleren Weg, dies in unsicherem Code zu tun:
public static class StringSupport
{
private static readonly int _charSize = sizeof(char);
public static unsafe byte[] GetBytes(string str)
{
if (str == null) throw new ArgumentNullException(nameof(str));
if (str.Length == 0) return new byte[0];
fixed (char* p = str)
{
return new Span<byte>(p, str.Length * _charSize).ToArray();
}
}
public static unsafe string GetString(byte[] bytes)
{
if (bytes == null) throw new ArgumentNullException(nameof(bytes));
if (bytes.Length % _charSize != 0) throw new ArgumentException($"Invalid {nameof(bytes)} length");
if (bytes.Length == 0) return string.Empty;
fixed (byte* p = bytes)
{
return new string(new Span<char>(p, bytes.Length / _charSize));
}
}
}
Beachten Sie, dass die Bytes eine UTF-16-codierte Zeichenfolge darstellen (in C # land "Unicode" genannt).
Ein schnelles Benchmarking zeigt, dass die obigen Methoden etwa fünfmal schneller sind als ihre Implementierungen von Encoding.Unicode.GetBytes (...)/GetString (...) für mittelgroße Zeichenfolgen (30-50 Zeichen) und noch schneller für größere Zeichenfolgen. Diese Methoden scheinen auch schneller zu sein als die Verwendung von Zeigern mit Marshal.Copy (..) oder Buffer.MemoryCopy (...).
Aufbauend auf ALis Antwort würde ich eine Erweiterungsmethode empfehlen, mit der Sie optional die Codierung übergeben können, die Sie verwenden möchten:
using System.Text;
public static class StringExtensions
{
/// <summary>
/// Creates a byte array from the string, using the
/// System.Text.Encoding.Default encoding unless another is specified.
/// </summary>
public static byte[] ToByteArray(this string str, Encoding encoding = Encoding.Default)
{
return encoding.GetBytes(str);
}
}
Und benutze es wie folgt:
string foo = "bla bla";
// default encoding
byte[] default = foo.ToByteArray();
// custom encoding
byte[] unicode = foo.ToByteArray(Encoding.Unicode);
Diese Arbeit für mich, danach konnte ich mein Bild in ein Bytea-Feld in meiner Datenbank stellen.
using (MemoryStream s = new MemoryStream(DirEntry.Properties["thumbnailphoto"].Value as byte[]))
{
return s.ToArray();
}