首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何对MySQL查询进行排队,使其成为顺序查询而不是并发查询,并防止过多的I/O使用?

如何对MySQL查询进行排队,使其成为顺序查询而不是并发查询,并防止过多的I/O使用?
EN

Stack Overflow用户
提问于 2011-11-30 01:50:17
回答 4查看 1.6K关注 0票数 0

我有多个独立的进程,每个进程都向MySQL数据库提交大容量插入查询(数百万行),但是让它们并发运行要比按顺序运行慢得多。

如何限制这些查询的执行,以便一次只能按顺序执行一个查询?

我曾想过检查PROCESSLIST是否包含任何正在运行的查询,但这可能不是真正的先来、先排队、先服务的正确排队查询的最佳方式。

我正在使用C#和.NET的MySQL连接器。

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2020-06-23 16:54:33

我不确定这是否会有帮助,但我来看看。我遇到了一个类似的问题,我的程序抛出了异常,因为MySql查询顺序混乱。因此,我决定按顺序运行查询,这样后续查询就不会失败。我在这里找到了一个解决方案。https://michaelscodingspot.com/c-job-queues/ -

代码语言:javascript
复制
public class job_queue
    {
        private ConcurrentQueue<Action> _jobs = new ConcurrentQueue<Action>();
        private bool _delegateQueuedOrRunning = false;
        public void Enqueue(Action job)
        {
            lock (_jobs)
            {
                _jobs.Enqueue(job);
                if (!_delegateQueuedOrRunning)
                {
                    _delegateQueuedOrRunning = true;
                    ThreadPool.UnsafeQueueUserWorkItem(ProcessQueuedItems, null);
                }
            }
        }
        private void ProcessQueuedItems(object ignored)
        {
            while (true)
            {
                Action item;
                lock (_jobs)
                {
                    if (_jobs.Count == 0)
                    {
                        _delegateQueuedOrRunning = false;
                        break;
                    }
                    _jobs.TryDequeue(out item);
                }
                try
                {
                    //do job
                    item();
                }
                catch
                {
                    ThreadPool.UnsafeQueueUserWorkItem(ProcessQueuedItems, null);
                    throw;
                }
            }
        }
    }

这是一个在队列中一个接一个地运行方法的类。并将包含Mysql查询的方法添加到job_queue by。

代码语言:javascript
复制
var mysql_tasks= new job_queue();
mysql_tasks.Enqueue(() => { Your_MYSQL_METHOD_HERE(); });
票数 1
EN

Stack Overflow用户

发布于 2011-11-30 02:02:33

我猜您使用的是InnoDb (它允许您进行并发写入)。MyISAM只有表级锁定,因此将对写入进行排队。

我推荐一种类似于ruakh的方法,但是您可以在数据库中使用一个表来管理锁定。该表的名称类似于lock_control

就在您尝试对表进行大容量插入之前,您在这个lock_control表上请求了一个LOCK TABLES lock_control WRITE。如果您被授予了锁,则继续批量写入,然后释放锁。如果表被另一个线程写锁定,那么LOCK TABLES命令将阻塞,直到释放锁为止。

您可以使用直接插入到的表来执行此锁定,但我相信在您持有锁的同时,也不会有其他线程能够读取该表。

在数据库而不是文件系统中进行这种锁定的优点是,您可以从多个客户端机器插入数据,而且在MySQL中处理所有的锁定/插入感觉会更简单一些。

票数 2
EN

Stack Overflow用户

发布于 2011-11-30 01:57:07

创建一个Bulk insert服务/类,让客户端在其中抛出数据。

它一次只做一个。如果您需要,消息返回完成。

你不想把你的数据库阻塞到一个线程上,这会杀死其他所有的东西。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8315327

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档