在 Windows 关闭时将 Python 存储集保存到文件? [英] Python Save Sets To File On Windows Shutdown?

查看:63
本文介绍了在 Windows 关闭时将 Python 存储集保存到文件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果 Windows 即将关闭/重新启动/注销/睡眠,我不想丢失我的设置,是否可以在关闭前保存它?或者是否有另一种方法可以保存信息而不必担心它会在 Windows 关闭时丢失?JSON、CSV、数据库?有什么吗?

I do not want to lose my sets if windows is about to shutdown/restart/log off/sleep, Is it possible to save it before shutdown? Or is there an alternative to save information without worring it will get lost on windows shutdown? JSON, CSV, DB? Anything?

s = {1,2,3,4}

with open("s.pick","wb") as f: # pickle it to file when PC about to shutdown to save information
    pickle.dump(s,f)

推荐答案

如果windows即将关闭/重启/注销/睡眠,我不想丢失我的设置,是否可以在关闭前保存?

I do not want to lose my sets if windows is about to shutdown/restart/log off/sleep, Is it possible to save it before shutdown?

是的,如果您构建了带有消息循环的应用程序,您可以收到 WM_QUERYENDSESSION 消息.如果您想要一个 GUI,大多数 GUI 库可能会以自己的方式进行包装.如果您不需要 GUI,最简单的解决方案可能是使用 PyWin32.在文档的某个地方有一个关于创建隐藏窗口和编写简单消息循环的教程.只需在主线程上执行此操作,然后在后台线程上执行真正的工作,并在 WM_QUERYENDSESSION 消息传入时向后台线程发出信号.

Yes, if you've built an app with a message loop, you can receive the WM_QUERYENDSESSION message. If you want to have a GUI, most GUI libraries will probably wrap this up in their own way. If you don't need a GUI, your simplest solution is probably to use PyWin32. Somewhere in the docs there's a tutorial on creating a hidden window and writing a simple message loop. Just do that on the main thread, and do your real work on a background thread, and signal your background thread when a WM_QUERYENDSESSION message comes in.

或者,更简单的是,正如 Evgeny Prokurat 建议的那样,只需使用 SetConsoleCtrlHandler(再次通过 PyWin32).这也可以捕获 ^C、^BREAK 和用户关闭控制台,以及 WM_QUERYENDSESSION 捕获的注销和关闭消息.更重要的是,它不需要消息循环,所以如果你没有任何其他需要,那就简单多了.

Or, much more simply, as Evgeny Prokurat suggests, just use SetConsoleCtrlHandler (again through PyWin32). This can also catch ^C, ^BREAK, and the user closing your console, as well as the logoff and shutdown messages that WM_QUERYENDSESSION catches. More importantly, it doesn't require a message loop, so if you don't have any other need for one, it's a lot simpler.

或者是否有另一种方法可以保存信息而不必担心它会在 Windows 关闭时丢失?JSON、CSV、数据库?有什么吗?

Or is there an alternative to save information without worring it will get lost on windows shutdown? JSON, CSV, DB? Anything?

文件格式不会神奇地解决任何问题.但是,数据库可能有两个优点.

The file format isn't going to magically solve anything. However, a database could have two advantages.

首先,您可以通过尽可能多地写作来减少问题.但是对于大多数文件格式,这意味着尽可能频繁地重写整个文件,这将非常慢.解决方案是流式传输到更简单的日志"文件,减少将其打包到真实文件中的频率,并在每次发布时查找剩余的日志.您可以手动执行此操作,但数据库通常会自动为您执行此操作.

First, you can reduce the problem by writing as often as possible. But with most file formats, that means rewriting the whole file as often as possible, which will be very slow. The solution is to streaming to a simpler "journal" file, packing that into the real file less often, and looking for a leftover journal at every launch. You can do that manually, but a database will usually do that for you automatically.

第二,如果你在写入过程中被杀死,你最终会得到半个文件.您可以通过原子写入技巧来解决这个问题——写一个临时文件,然后用临时文件替换旧文件——但这在 Windows 上很难做到(尤其是使用 Python 2.x)(参见 正确进行原子写入),同样,数据库通常会这样做给你.

Second, if you get killed in the middle of a write, you end up with half a file. You can solve that by the atomic writing trick—write a temporary file, then replace the old file with the temporary—but this is hard to get right on Windows (especially with Python 2.x) (see Getting atomic writes right), and again, a database will usually do it for you.

执行此操作的正确"方法是创建一个带有 msgproc 的新窗口类,该类在 WM_QUERYENDSESSION 上分派到您的处理程序.正如 MFC 比原始 Win32 API 代码更容易,win32ui(包装 MFC)使这比 win32api/win32gui(包装原始Win32 API).并且您可以找到很多示例(例如,快速搜索pywin32 msgproc 示例"会找到诸如 ,搜索python win32ui"和类似的术语也一样有效).

The "right" way to do this is to create a new window class with a msgproc that dispatches to your handler on WM_QUERYENDSESSION. Just as MFC makes this easier than raw Win32 API code, win32ui (which wraps MFC) makes this easier than win32api/win32gui (which wraps raw Win32 API). And you can find lots of samples for that (e.g., a quick search for "pywin32 msgproc example" turned up examples like this, and searches for "python win32ui" and similar terms worked just as well).

但是,在这种情况下,您没有想要充当普通窗口的窗口,因此直接转到低级别并编写快速而肮脏的消息循环可能会更容易.不幸的是,要找到示例代码要困难得多——您基本上必须在本机 API 中搜索 C 示例代码(例如 在 MSDN 上创建消息循环),然后找出如何使用 pywin32 文档.不太理想,特别是如果你不知道 C,但不是那么难.下面是一个让您入门的示例:

However, in this case, you don't have a window that you want to act like a normal window, so it may be easier to go right to the low level and write a quick&dirty message loop. Unfortunately, that's a lot harder to find sample code for—you basically have to search the native APIs for C sample code (like Creating a Message Loop at MSDN), then figure out how to translate that to Python with the pywin32 documentation. Less than ideal, especially if you don't know C, but not that hard. Here's an example to get you started:

def msgloop():
    while True:
        msg = win32gui.GetMessage(None, 0, 0)
        if msg and msg.message == win32con.WM_QUERYENDSESSION:
            handle_shutdown()
        win32api.TranslateMessage(msg)
        win32api.DispatchMessage(msg)
        if msg and msg.message == win32con.WM_QUIT:
            return msg.wparam

worker = threading.Thread(real_program)
worker.start()
exitcode = msgloop()
worker.join()
sys.exit(exitcode)

我没有展示如何创建最小隐藏窗口"部分,或者如何通知工作人员停止使用,例如,threading.Condition,因为还有很多(并且更容易找到)这些零件的好样品;这是很难找到的部分.

I haven't shown the "how to create a minimal hidden window" part, or how to signal the worker to stop with, e.g., a threading.Condition, because there are a lot more (and easier-to-find) good samples for those parts; this is the tricky part to find.

这篇关于在 Windows 关闭时将 Python 存储集保存到文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆