【发布时间】:2020-04-21 18:13:00
【问题描述】:
我正在为 Minecraft 服务器开发一个插件,您可以在其中将红石连接到互联网。该插件通过使用游戏内置的讲台来发送/接收任意红石信号。它使用 MQTT 协议与 Internet 通信。
目前,我有一个名为 LecternHandlers 的讲台加载程序,它为每个创建的讲台加载一个 LecternHandler 的新实例。 LecternHandler 的所有实例都存储在 ArrayList 中,格式为 <Location, LecternHandler> 的键/值,其中 Location 是讲台的位置(此位置存储世界和坐标,是 Bukkit api 的内置功能)。
至于数据存储,我使用 MySQL 将讲台和播放器设置保存在两个不同的表中。讲台表存储诸如讲台的位置及其 id 等信息。 player 表存储诸如要连接的 MQTT 代理、是否使用 tls、身份验证详细信息等信息...
我想做的是能够即时更新播放器设置以及卸载和重新加载讲台。目前,我必须遍历每个LecternHandler 并检查它是否属于播放器,然后将其卸载并重新加载。然后LecternHandler 将从 MySQL 中检索新设置。
我相信,如果我一次循环遍历数千个甚至数万个讲台,尤其是玩家自己有数千个讲台时,这可能会导致性能问题。
如何解决潜在的性能问题?
如果您想查看代码本身,请在 GPL-3 下my project is on Github 感兴趣的人。
我的目标是让这个插件在处理大量讲台时非常有效,这样人们就不会因为他们想要的简洁功能而让他们的服务器变慢。
【问题讨论】:
-
您熟悉元编程吗?我会改写。你知道橡皮鸭吗? Say hello to my lil' friend.
-
不,我不熟悉元编程。虽然我知道橡皮鸭是什么,但我也不确定它们与编程有什么关系,尽管如果我熟悉元编程可能会有意义。
-
您尝试过多线程还是想要优化?
-
@user 我目前使用回调将函数传递给我用于 MQTT 的 HiveMQ 库。除了回调之外,我的代码中没有任何支持异步的函数。至于从回调中更新讲台,我必须使用 Bukkit 的调度程序将更新讲台的代码放在主线程上,因为由于 Minecraft 当前处理块操作的方式,不允许操作世界上的块。我想说,我正在寻找有关如何有效地操作大量数据的一小部分的指针。
-
当我说不允许操作块时,我的意思是不允许异步操作。我将看到关于使讲台处理程序加载和操作本身异步,因为它不接触 bukkit api,除了现有的回调。