繁体   English   中英

c#FileSystemWatcher Created事件未针对所有创建的文件触发

[英]c# FileSystemWatcher Created event not firing for all files created

我想为目录中创建的所有文件将文件信息插入数据库。 如果我在目录中放置少量文件,我的程序将执行此操作,但是如果一次在目录中放置大量文件,则无法全部获取(我没有进行大量测试,但只插入了大约当我尝试一次在目录中删除800个文件时,数据库中有200个名称)。

这是我的代码:

static void Main(string[] args)
{
    // Create a new FileSystemWatcher and set its properties.
    FileSystemWatcher watcher = new FileSystemWatcher();
    watcher.Path = @"C:\dropDirectory";

    // Add event handlers.
    watcher.Created += new FileSystemEventHandler(OnChanged);

    // Begin watching.
    watcher.EnableRaisingEvents = true;

    while(DateTime.Now.Hour < 10);
}

private static void OnChanged(object source, FileSystemEventArgs e)
{
    string strInsert = "INSERT INTO  Files (Filename) VALUES ('" + e.Name + "')";
    string strConnection = "Server = server_name; Database = database_name; User Id = user_id; Password = password;";
    using (SqlConnection con = new SqlConnection(strConnection))
    {
        using (SqlCommand cmd = new SqlCommand(strInsert, con))
        {   
            con.Open();
            cmd.ExecuteScalar();
        }
    }
}

我需要进行哪些更改,以便无论是否放置了多少文件,都将为目标目录中放置的每个文件调用OnChanged方法? 提前致谢。

您的问题是缓冲区大小,以及它众所周知且已记录的问题

FileSystemWatcher使用带有一些相关标志的ReadDirectoryChangesW WinApi调用

首次调用ReadDirectoryChangesW ,系统会分配一个缓冲区来存储更改信息。 该缓冲区与目录句柄相关联,直到它被关闭并且其大小在其生命周期内保持不变。 在两次调用此函数之间发生的目录更改将添加到缓冲区中,然后在下一次调用时返回。 如果缓冲区溢出,则将丢弃缓冲区的全部内容

FileSystemWatcher中的类似物是FileSystemWatcher.InternalBufferSize属性

备注您可以将缓冲区设置为4 KB或更大,但不能超过64 KB。 如果您尝试将InternalBufferSize属性设置为小于4096字节,则将丢弃您的值,并将InternalBufferSize属性设置为4096字节。 为了获得最佳性能,请在基于Intel的计算机上使用4 KB的倍数。

系统将文件更改通知组件,并将这些更改存储在组件创建并传递给API的缓冲区中。 每个事件最多可以使用16个字节的内存 ,不包括文件名。 如果在短时间内有很多更改,缓冲区可能会溢出。 这将导致该组件无法跟踪目录中的更改 ,并且仅提供一揽子通知。 增加缓冲区的大小可以防止丢失文件系统更改事件。 但是,增加缓冲区大小是昂贵的,因为它来自无法调换到磁盘的非分页内存,因此请保持缓冲区尽可能小。 为了避免缓冲区溢出,请使用NotifyFilter和IncludeSubdirectories属性过滤掉不需要的更改通知

如果情况变得更糟,您可以混合使用轮询和跟踪,这使我几次摆脱困境。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM