Мне нужно написать unit test для метода, который берет поток, который поступает из текстового файла. Я хотел бы сделать что-то вроде этого:
Stream s = GenerateStreamFromString("a,b \n c,d");
public static Stream GenerateStreamFromString(string s)
{
var stream = new MemoryStream();
var writer = new StreamWriter(stream);
writer.Write(s);
writer.Flush();
stream.Position = 0;
return stream;
}
Не забудьте использовать Использование:
using (var stream = GenerateStreamFromString("a,b \n c,d"))
{
// ... Do stuff to stream
}
О StreamWriter
не используется. StreamWriter
- это всего лишь оболочка вокруг базового потока и не использует никаких ресурсов, которые необходимо утилизировать. Метод Dispose
закрывает базовый Stream
который пишет StreamWriter
. В этом случае мы хотим вернуть MemoryStream
.
В.NET 4.5 теперь есть перегрузка для StreamWriter
которая поддерживает открытый поток после того, как автор удален, но этот код делает то же самое и работает с другими версиями.NET.
См. Есть ли способ закрыть StreamWriter без закрытия BaseStream?
GenerateStreamFromString
вы не используете Using с StreamWriter. Для этого есть причина?
Другое решение:
public static MemoryStream GenerateStreamFromString(string value)
{
return new MemoryStream(Encoding.UTF8.GetBytes(value ?? ""));
}
Добавьте это в статический класс классов:
public static Stream ToStream(this string str)
{
MemoryStream stream = new MemoryStream();
StreamWriter writer = new StreamWriter(stream);
writer.Write(str);
writer.Flush();
stream.Position = 0;
return stream;
}
Это добавляет функцию расширения, поэтому вы можете просто:
using (var stringStream = "My string".ToStream())
{
// use stringStream
}
StreamWriter
. Исправление состояло в том, чтобы использовать другой конструктор - тот, который позволял мне указывать оставлять открытыми .
public Stream GenerateStreamFromString(string s)
{
return new MemoryStream(Encoding.UTF8.GetBytes(s));
}
Используйте класс MemoryStream
, вызывая Encoding.GetBytes
, чтобы сначала преобразовать вашу строку в массив байтов.
Вам понадобится TextReader
в потоке? Если это так, вы можете напрямую передать StringReader
и обходить шаги MemoryStream
и Encoding
.
Я использовал сочетание ответов вроде этого:
public static Stream ToStream(this string str, Encoding enc = null)
{
enc = enc ?? Encoding.UTF8;
return new MemoryStream(enc.GetBytes(str ?? ""));
}
И затем я использую его следующим образом:
String someStr="This is a Test";
Encoding enc = getEncodingFromSomeWhere();
using (Stream stream = someStr.ToStream(enc))
{
// Do something with the stream....
}
Здесь вы идете:
private Stream GenerateStreamFromString(String p)
{
Byte[] bytes = UTF8Encoding.GetBytes(p);
MemoryStream strm = new MemoryStream();
strm.Write(bytes, 0, bytes.Length);
return strm;
}
Я думаю, вы можете воспользоваться MemoryStream. Вы можете заполнить его строковыми байтами, которые вы получите, используя метод GetBytes Класс кодирования.
Мы используем методы расширения, перечисленные ниже. Я думаю, вы должны заставить разработчика принять решение о кодировании, поэтому есть меньше магии.
public static class StringExtensions {
public static Stream ToStream(this string s) {
return s.ToStream(Encoding.UTF8);
}
public static Stream ToStream(this string s, Encoding encoding) {
return new MemoryStream(encoding.GetBytes(s ?? ""));
}
}
return ToStream(s, Encoding.UTF8);
, В текущей реализации ( return s.ToStream(Encoding.UTF8);
разработчик вынужден усерднее думать, чтобы понять код, и кажется, что случай s == null
не NullReferenceException
и выдает NullReferenceException
.
Немного измененная версия методов расширения, предложенная в комментарии ответа @JoelNet и ответа @Shaun Bowe. Потому что я согласен с комментарием @Palec.
public static Stream ToStream(this string value) => ToStream(value, Encoding.UTF8);
public static Stream ToStream(this string value, Encoding encoding) => new MemoryStream(encoding.GetBytes(value ?? string.Empty));
Хорошая комбинация расширений строк:
public static byte[] GetBytes(this string str)
{
byte[] bytes = new byte[str.Length * sizeof(char)];
System.Buffer.BlockCopy(str.ToCharArray(), 0, bytes, 0, bytes.Length);
return bytes;
}
public static Stream ToStream(this string str)
{
Stream StringStream = new MemoryStream();
StringStream.Read(str.GetBytes(), 0, str.Length);
return StringStream;
}
/// <summary>
/// Get Byte[] from String
/// </summary>
/// <param name="str"></param>
/// <returns></returns>
public 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;
}
/// <summary>
/// Get Stream from String
/// </summary>
/// <param name="str"></param>
/// <returns></returns>
public static Stream GetStream(string str)
{
return new MemoryStream(GetBytes(str));
}
StringReaderStream
в stackoverflow.com/a/55170901/254109