相关疑难解决方法(0)

如何确保所有数据都已物理写入磁盘?

据我所知,.NET FileStream的Flush方法只将当前缓冲区写入磁盘,但依赖于Windows的磁盘驱动程序和硬盘固件,这并不能保证数据实际上是物理写入磁盘的.

是否有.NET或Win32方法可以给我这个保证?因此,如果在调用此方法后一纳秒之后出现断电,我仍然可以确定一切正常吗?

.net c# flush filestream

20
推荐指数
2
解决办法
2万
查看次数

FileSystemWatcher不报告锁定文件中的更改

我正在使用FileSystemWatcher监视文件夹,如下所示:

watcher = new FileSystemWatcher(folder);
watcher.NotifyFilter = NotifyFilters.Size;
watcher.Changed += changedCallback;
Run Code Online (Sandbox Code Playgroud)

当我在该文件夹中的记事本中打开一个新文件并保存时,我会收到通知.如果我继续写作然后保存,我会收到通知.如果我保存它关闭文件,我会收到通知.正是我想要的.

但是,事实证明,如果我在该文件夹中创建一个文件并将其共享模式设置为FileShare.Read,然后我写入它,则在文件关闭之前我不会收到任何通知.另一种解决方法是打开文件(例如在记事本中),这显然会导致其状态更新,然后我的监控应用程序会收到通知.另一种解决方法是我可以在Windows资源管理器中执行刷新,这再次导致文件状态更新.

有趣的是,如果我在进行更改时查看Windows资源管理器,我会注意到:

  1. 如果共享文件进行读写,则一旦保存,它的大小将立即在Windows资源管理器中更新.
  2. 如果共享文件仅供读取,则不会在Windows资源管理器中立即更新其大小,除非我手动刷新窗口.

因此,我的监控应用程序似乎与Windows资源管理器共享相同的行为.我正在考虑运行一个只扫描文件夹中文件的线程,但我想知道在这种情况下是否还有更优雅的事情要做.

顺便说一下,我正在使用Win7,我不确定这个问题是否也会在其他Windows版本上发生.

谢谢!

编辑:在C++中使用ReadDirectoryChanges得到了相同的结果.实现我之前谈到的线程并没有帮助.我想知道Windows资源管理器中的F5究竟是做什么的,因为它确实会导致报告更改.

c# filesystemwatcher

13
推荐指数
1
解决办法
5310
查看次数

如何在C#winform app中进行非缓存文件写入

我正在尝试确定最坏情况下的磁盘速度,所以我编写了以下函数.

static public decimal MBytesPerSec(string volume)
{
    string filename = volume + "\\writetest.tmp";

    if (System.IO.File.Exists(filename))
        System.IO.File.Delete(filename);

    System.IO.StreamWriter file = new System.IO.StreamWriter(filename);

    char[] data = new char[64000];
    Stopwatch watch = new Stopwatch();
    watch.Start();

    int i = 0;

    for (; i < 1000; i++)
    {
        file.Write(data);
        if (watch.ElapsedMilliseconds > 2000)
        {
            break;
        }
    }

    watch.Stop();
    file.Close();

    System.IO.File.Delete(volume + "\\test.txt");
    decimal mbytessec = (i * 64 / watch.ElapsedMilliseconds);
    return mbytessec;
}
Run Code Online (Sandbox Code Playgroud)

该函数工作正常,但写入缓存,因此速度不是最坏的情况.

在WIN32 C++中,我只需使用选项创建文件FILE_FLAG_NO_BUFFERING,FILE_FLAG_WRITE_THROUGH然后确保遵循非缓存写入规则(以扇区大小偏移写入文件,最少写入4k)

我发现了一篇讨论.NET技术的文章. …

.net c# file winforms

13
推荐指数
1
解决办法
5030
查看次数

Servlet缓冲响应尽管调用flush()

我们有一个系统,客户端发出HTTP GET请求,系统对后端进行一些处理,压缩结果,然后将其发送给客户端.由于处理可能需要一些时间,我们将其作为ZipOutputStream包装发送response.getOutputStream().

但是,当我们在第一个中有非常少量的数据ZipEntry,而第二个条目需要很长时间时,客户端使用的浏览器会超时.我们已经尝试刷新流缓冲区,但是在向流写入至少1000个字节之前,似乎没有响应发送到浏览器.奇怪的是,一旦发送了前1000个字节,后续的刷新似乎工作正常.

我尝试将代码拆解为裸露的示例:

protected void doGet(HttpServletRequest request,
        HttpServletResponse response) throws ServletException, IOException {
    try {
        ZipOutputStream _zos = new ZipOutputStream( response.getOutputStream());
        ZipEntry _ze = null;
        long startTime = System.currentTimeMillis();
        long _lByteCount = 0;

        response.setContentType("application/zip");

        while (_lByteCount < 2000) {
            _ze = new ZipEntry("foo");
            _zos.putNextEntry( _ze );

            //writes 100 bytes and then waits 10 seconds
            _lByteCount += StreamWriter.write( 
                    new ByteArrayInputStream(DataGenerator.getOutput().toByteArray()),
                    _zos );
            System.out.println("Zip: " + _lByteCount + " Time: " + ((System.currentTimeMillis() - startTime) …
Run Code Online (Sandbox Code Playgroud)

java tomcat servlets

9
推荐指数
1
解决办法
9513
查看次数

标签 统计

c# ×3

.net ×2

file ×1

filestream ×1

filesystemwatcher ×1

flush ×1

java ×1

servlets ×1

tomcat ×1

winforms ×1