有一些代码通过调用GetBuffer()将数据直接写入MemoryStream对象的数据缓冲区.它还适当地使用和更新Position和SetLength()属性.
此代码在99.9999%的时间内正常工作.从字面上看.只有每隔这么多的100,000次迭代才能实现.具体问题是MemoryStream的Position属性突然返回零而不是适当的值.
但是,添加了检查0的代码并抛出异常,其中包括在单独的方法中记录MemoryStream属性(如位置和长度).那些返回正确的值.在同一方法中进一步添加日志记录表明,当出现这种罕见情况时,Position在此特定方法中仅为零.
好的.显然,这必须是一个线程问题.而且很可能是编译器优化问题.
但是,这个软件的本质是它由调度程序的"任务"组织,因此几个实际的O/S线程中的任何一个都可以在任何给定时间运行此代码 - 但一次不得超过一个.
所以我的猜测通常会发生同样的线程不断用于此方法,然后在极少数情况下使用不同的线程.(只需编写想法,通过捕获和比较线程ID来测试这个理论.)
然后由于编译器优化,不同的线程永远不会得到正确的值.它得到一个"陈旧"的价值.
通常在这种情况下,我会将"volatile"关键字应用于相关变量,以查看是否可以修复它.但在这种情况下,变量位于MemoryStream对象中.
有没有人有任何其他想法?或者这是否意味着我们必须实现自己的MemoryStream对象?
真诚的,韦恩
编辑:只运行一个测试,计算此方法的调用总数,并计算ManagedThreadId与上次调用的次数不同的次数.它几乎完全是50%的时间切换线程 - 在它们之间交替.所以我上面的理论几乎肯定是错的,或者错误会更频繁地发生.
编辑:这个错误很少发生,它需要将近一个星期的运行没有错误之前感到有任何信心,它真的消失了.相反,最好运行实验来确切地确定问题的本质.
编辑:当前锁定是通过使用MemoryStream的5种方法中的每一种中的lock()语句来处理的.
我不能让这个工作.我有一个MemoryStream对象.此类有一个Position属性,可以告诉您已读取的字节数.
我想要做的是删除0和位置1之间的所有字节
我试过这个:
MemoryStream ms = ...
ms.SetLength(ms.Length - ms.Position);
Run Code Online (Sandbox Code Playgroud)
但在某些时候我的数据被破坏了.
所以我最终做到了这一点
MemoryStream ms = ...
byte[] rest = new byte[ms.Length - ms.Position];
ms.Read(rest, 0, (int)(ms.Length - ms.Position));
ms.Dispose();
ms = new MemoryStream();
ms.Write(rest, 0, rest.Length);
Run Code Online (Sandbox Code Playgroud)
哪个有效,但效率不高.
任何想法我怎么能让这个工作?
谢谢
我有四个要合并的MemoryStream数据,然后打开pdfDocument,而不创建单个文件.
可以将它们写入文件然后合并它们但这样做会很糟糕,这也会导致一些问题,所以我想避免这种情况.
但是,我找不到将MemoryStreams与iText5 for .NET合并的方法.
现在,这是我用文件做的方式:
private static void ConcatenateDocuments()
{
var stream = new MemoryStream();
var readerFrontPage = new PdfReader(Folder + FrontPageName);
var readerDocA = new PdfReader(Folder + docA);
var readerDocB = new PdfReader(Folder + DocB);
var readerAppendix = new PdfReader(Folder + Appendix);
var pdfCopyFields = new PdfCopyFields(stream);
pdfCopyFields.AddDocument(readerFrontPage);
pdfCopyFields.AddDocument(readerDocA );
pdfCopyFields.AddDocument(readerDocB);
pdfCopyFields.AddDocument(readerAppendix);
pdfCopyFields.Close();
SavePdf(stream, FilenameReport);
}
Run Code Online (Sandbox Code Playgroud)
由于我需要删除文件的使用,因此我保留了MemoryStream,因为不同的部分是从不同的资源构建的.所以我引用了这些内存流.
如何才能做到这一点?
是否有可能从任何html文件中获取由wkhtmltopdf创建的pdf流,并在IE/Firefox/Chrome等中弹出下载对话框?
目前我通过此代码获取我的输出流:
public class Printer
{
public static MemoryStream GeneratePdf(StreamReader Html, MemoryStream pdf, Size pageSize)
{
Process p;
StreamWriter stdin;
ProcessStartInfo psi = new ProcessStartInfo();
psi.FileName = @"C:\PROGRA~1\WKHTML~1\wkhtmltopdf.exe";
// run the conversion utility
psi.UseShellExecute = false;
psi.CreateNoWindow = true;
psi.RedirectStandardInput = true;
psi.RedirectStandardOutput = true;
psi.RedirectStandardError = true;
// note that we tell wkhtmltopdf to be quiet and not run scripts
psi.Arguments = "-q -n --disable-smart-shrinking " + (pageSize.IsEmpty ? "" : "--page-width " + pageSize.Width + "mm --page-height " …Run Code Online (Sandbox Code Playgroud) 目前正在寻找Java和C#应用程序的接口.在Java中,我可以使用getShort(),getFloat()等等,从缓冲区中获得各种不同的数据类型.
在C#我使用的是a MemoryStream,但只有一个get()功能.有人知道数据类型甚至是模仿这个功能的类吗?
我试图从服务器路由返回一个图像,但我得到一个0字节的图像.我怀疑它与我如何使用它有关MemoryStream.这是我的代码:
[HttpGet]
[Route("edit")]
public async Task<HttpResponseMessage> Edit(int pdfFileId)
{
var pdf = await PdfFileModel.PdfDbOps.QueryAsync((p => p.Id == pdfFileId));
IEnumerable<Image> pdfPagesAsImages = PdfOperations.PdfToImages(pdf.Data, 500);
MemoryStream imageMemoryStream = new MemoryStream();
pdfPagesAsImages.First().Save(imageMemoryStream, ImageFormat.Png);
HttpResponseMessage response = new HttpResponseMessage();
response.Content = new StreamContent(imageMemoryStream);
response.Content.Headers.ContentType = new MediaTypeHeaderValue("image/png");
response.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment")
{
FileName = pdf.Filename,
DispositionType = "attachment"
};
return response;
}
Run Code Online (Sandbox Code Playgroud)
通过调试,我已经验证了该PdfToImages方法是否正常工作,并且imageMemoryStream从该行填充了数据
pdfPagesAsImages.First().Save(imageMemoryStream, ImageFormat.Png);
Run Code Online (Sandbox Code Playgroud)
但是在运行它时,我收到一个正确命名但是为0字节的附件.为了接收整个文件,我需要更改什么?我认为这很简单,但我不确定是什么.提前致谢.
我正在尝试在ASP.NET Web API控制器中返回文件。此文件是动态生成的PDF,保存在MemoryStream中。
客户端(浏览器)成功接收到文件,但是当我打开文件时,我看到所有页面都完全空白。
问题是,如果我使用相同的MemoryStream并将其写入文件,则此磁盘文件将正确显示,因此我认为问题与通过Web传输文件有关。
我的控制器如下所示:
[HttpGet][Route("export/pdf")]
public HttpResponseMessage ExportAsPdf()
{
MemoryStream memStream = new MemoryStream();
PdfExporter.Instance.Generate(memStream);
memStream.Position = 0;
HttpResponseMessage result = new HttpResponseMessage(HttpStatusCode.OK);
result.Content = new ByteArrayContent(memStream.ToArray()); //OR: new StreamContent(memStream);
return result;
}
Run Code Online (Sandbox Code Playgroud)
尝试一下,如果我将流写入磁盘,则会正确显示:
[HttpGet][Route("export/pdf")]
public HttpResponseMessage ExportAsPdf()
{
MemoryStream memStream = new MemoryStream();
PdfExporter.Instance.Generate(memStream);
memStream.Position = 0;
using (var fs = new FileStream("C:\\Temp\\test.pdf", FileMode.OpenOrCreate, FileAccess.ReadWrite))
{
memStream.CopyTo(fs);
}
return null;
}
Run Code Online (Sandbox Code Playgroud)
不同之处在于:
如果我比较两个文件的内容,主要区别是:
左侧是通过Web传输的PDF。在右侧,PDF已保存到磁盘。
我的代码有问题吗?也许与编码有关?
谢谢!
我需要从Web服务返回存储在磁盘上的映像.
在我的控制器中,我执行一些搜索操作并发送文件.这是我的代码.
public HttpResponseMessage Get([FromUri]ShowImageRequest req)
{
// .......................
// .......................
// load image file
var imgStream = new MemoryStream();
using (Image image = Image.FromFile(fullImagePath))
{
image.Save(imgStream, ImageFormat.Jpeg);
}
imgStream.Seek(0, SeekOrigin.Begin); // it does not work without this
var res = new HttpResponseMessage(HttpStatusCode.OK);
res.Content = new StreamContent(imgStream);
res.Content.Headers.ContentType = new ediaTypeHeaderValue("image/jpeg");
return res;
}
Run Code Online (Sandbox Code Playgroud)
如果我不添加这一行,我会在fiddler响应体长0中看到
imgStream.Seek(0, SeekOrigin.Begin);
Run Code Online (Sandbox Code Playgroud)
否则它有效.我错过了什么,为什么我需要这样做?
我正在开发一个 .NET Core 项目,我应该从记录中创建一个电子表格文件并下载它而不将它保存在服务器中。搜索上面的标题并没有多大帮助,但提供了一些指导。此外,ASP.NET 中使用的大多数方法在 .NET Core 中都不起作用。所以,我终于可以想出一个工作正常的解决方案。我将在下面的答案中为那些和我一样进行相同搜索的人分享它。
我想使用 asp.net core 在浏览器中播放视频
在html中我有
<video width="320" height="240" controls>
<source src="http://localhost:55193/api/VideoPlayer/Download" type="video/mp4">
Your browser does not support the video tag.
</video>
Run Code Online (Sandbox Code Playgroud)
并在asp.net core 2中
[HttpGet]
[Route("Download")]
public async Task<IActionResult> Download()
{
var path = @"d:\test\somemovie.mp4";
var memory = new MemoryStream();
using (var stream = new FileStream(@"d:\test\somemovie.mp4", FileMode.Open, FileAccess.Read, FileShare.ReadWrite, 65536, FileOptions.Asynchronous | FileOptions.SequentialScan))
{
await stream.CopyToAsync(memory);
}
memory.Position = 0;
return File(memory, "application/octet-stream", Path.GetFileName(path));
}
Run Code Online (Sandbox Code Playgroud)
此代码是否通过流播放文件(我的意思是逐块缓冲文件并播放)?
如果我想从用户设置播放器进度的任何位置播放文件,我该怎么做?
memorystream ×10
c# ×8
.net ×3
angularjs ×1
asp.net-core ×1
attachment ×1
bytebuffer ×1
c#-4.0 ×1
excel ×1
filestream ×1
itext ×1
merge ×1
routes ×1
volatile ×1
wkhtmltopdf ×1