【问题标题】:cx_Freeze app closes right away with no errorscx_Freeze 应用程序立即关闭,没有错误
【发布时间】:2019-06-03 08:10:28
【问题描述】:

我的cx_Freeze 应用程序在我打开它时关闭,并且没有打印任何错误。安装文件运行没有错误。我相信这与我的主要代码中的导入有关。我使用了 python 3.6.5 cx_Freeze 6.0b1 和 windows 10。

setup.py

import os
from cx_Freeze import setup, Executable

include_lst = []

package_lst = ['numpy', 'scipy', 'pulp', 'pubsub', 'sqlite3', 'pandas',
               'wx', 'functools', 'sklearn', 'numpy.core._methods']

exclude_lst = ['matplotlib', 'tkinter', 'PyQt4.QtSql', 'PyQt5',
               'PyQt4.QtNetwork', 'PyQt4.QtScript', 'sqlalchemy']

base = None

setup (
       name='test',
       version='0.01',
       author='test',
       author_email='Omitted',
       options={'build_exe':
                   {'packages': package_lst,
                    'excludes': exclude_lst,
                    'include_files': include_lst
                   }
                },
       executables=[Executable('main_.py',  base=base, icon=icon_file)]
       )

当我冻结这个基本示例时,它可以正常工作

main.py

import wx


class MasterPage (wx.Frame):
    def __init__(self, *args, **kwargs):
        wx.Frame.__init__(self, *args, **kwargs)

        self.createFrame()

    def createFrame(self):
        self.width, self.height = wx.GetDisplaySize()
        self.SetTitle('Test')
        self.SetSize(wx.Size((self.width-50, self.height-50)))
        self.SetMinSize((1080, 720))
        self.W, self.H = self.GetSize()
        self.Bind(wx.EVT_CLOSE, self.onQuit)
        self.Centre()

    def onQuit(self, event):
        """Checks to make sure the user wants to leave the program"""
        dlg = wx.MessageDialog(self,'Do you really want to quit?',
                           'Confirm Exit',
                            wx.ICON_QUESTION|wx.OK|wx.CANCEL )
        result = dlg.ShowModal()
        dlg.Destroy
        if result == wx.ID_OK:
            self.Destroy()

if __name__.endswith('__main__'):
    app = wx.App()
    MasterPage(None).Show()
    app.MainLoop()

但是当我在import wx 行上方添加import pandasimport <any module> 时,cx_Freeze 应用程序一打开它就会关闭

main.py

import pandas
import wx


class MasterPage (wx.Frame):
    def __init__(self, *args, **kwargs):
        wx.Frame.__init__(self, *args, **kwargs)

        self.createFrame()

    def createFrame(self):
        self.width, self.height = wx.GetDisplaySize()
        self.SetTitle('Test')
        self.SetSize(wx.Size((self.width-50, self.height-50)))
        self.SetMinSize((1080, 720))
        self.W, self.H = self.GetSize()
        self.Bind(wx.EVT_CLOSE, self.onQuit)
        self.Centre()

    def onQuit(self, event):
        """Checks to make sure the user wants to leave the program"""
        dlg = wx.MessageDialog(self,'Do you really want to quit?',
                           'Confirm Exit',
                            wx.ICON_QUESTION|wx.OK|wx.CANCEL )
        result = dlg.ShowModal()
        dlg.Destroy
        if result == wx.ID_OK:
            self.Destroy()

if __name__.endswith('__main__'):
    app = wx.App()
    MasterPage(None).Show()
    app.MainLoop()

我也尝试将导入放在 try except 语句中,它仍然无法打开并且没有错误打印

main.py

try:
    import pandas
except Exception as e:
    print(e)
import wx


class MasterPage (wx.Frame):
    def __init__(self, *args, **kwargs):
        wx.Frame.__init__(self, *args, **kwargs)

        self.createFrame()

    def createFrame(self):
        self.width, self.height = wx.GetDisplaySize()
        self.SetTitle('Test')
        self.SetSize(wx.Size((self.width-50, self.height-50)))
        self.SetMinSize((1080, 720))
        self.W, self.H = self.GetSize()
        self.Bind(wx.EVT_CLOSE, self.onQuit)
        self.Centre()

    def onQuit(self, event):
        """Checks to make sure the user wants to leave the program"""
        dlg = wx.MessageDialog(self,'Do you really want to quit?',
                           'Confirm Exit',
                            wx.ICON_QUESTION|wx.OK|wx.CANCEL )
        result = dlg.ShowModal()
        dlg.Destroy
        if result == wx.ID_OK:
            self.Destroy()

if __name__.endswith('__main__'):
    app = wx.App()
    MasterPage(None).Show()
    app.MainLoop()

我什至在import 语句之前和import 语句之后添加了一个打印语句,第一个打印语句运行然后应用程序关闭。

main.py

print('app started')
import pandas
print('import worked')
import wx


class MasterPage (wx.Frame):
    def __init__(self, *args, **kwargs):
        wx.Frame.__init__(self, *args, **kwargs)

        self.createFrame()

    def createFrame(self):
        self.width, self.height = wx.GetDisplaySize()
        self.SetTitle('Test')
        self.SetSize(wx.Size((self.width-50, self.height-50)))
        self.SetMinSize((1080, 720))
        self.W, self.H = self.GetSize()
        self.Bind(wx.EVT_CLOSE, self.onQuit)
        self.Centre()

    def onQuit(self, event):
        """Checks to make sure the user wants to leave the program"""
        dlg = wx.MessageDialog(self,'Do you really want to quit?',
                           'Confirm Exit',
                            wx.ICON_QUESTION|wx.OK|wx.CANCEL )
        result = dlg.ShowModal()
        dlg.Destroy
        if result == wx.ID_OK:
            self.Destroy()

if __name__.endswith('__main__'):
    app = wx.App()
    MasterPage(None).Show()
    app.MainLoop()

【问题讨论】:

    标签: python-3.x cx-freeze


    【解决方案1】:

    有趣的是,pandastkinter(而不是 wx)之间类似的明显导入冲突已发布在 Error when building executable from Python3.6 script importing pandas using cx_Freeze 中。

    1. 我不熟悉wx。首先,我认为您应该将base = "Win32GUI" 用于Windows 下的GUI 应用程序(参见cx_Freezedocumentation)。将base = None 替换为安装脚本中的以下行:

      # GUI applications require a different base on Windows (the default is for a console application).
      import sys
      base = None
      if sys.platform == "win32":
          base = "Win32GUI"
      
    2. 由于您已将scipy 添加到packages 选项列表中,您还需要将scipy.spatial.cKDTree 添加到excludes 选项列表中(参见this issue):

      exclude_lst = ['matplotlib', 'tkinter', 'PyQt4.QtSql', 'PyQt5',
                     'PyQt4.QtNetwork', 'PyQt4.QtScript', 'sqlalchemy',
                     'scipy.spatial.cKDTree']
      
    3. 您可能还需要将sqlite3.dll 添加到include_files 选项列表才能使用sqlite3(我不确定):

      PYTHON_INSTALL_DIR = os.path.dirname(os.path.dirname(os.__file__))
      include_lst = [(os.path.join(PYTHON_INSTALL_DIR, 'DLLs', 'sqlite3.dll'), os.path.join('lib', 'sqlite3.dll'))]
      
    4. 最后,我建议从cmd 提示符中启动您的应用程序,以确保收到所有错误消息:

      • 启动cmd 提示符(在开始菜单中输入cmd
      • 转到生成冻结可执行文件的构建目录
      • 启动冻结的可执行文件

    如果您仍然收到任何其他错误消息,请将其添加到您的问题中。

    【讨论】:

    • 您好 Jpeg,非常感谢您为此提供的所有帮助。我从 cmd 提示符运行它,它没有打印任何错误,它只会转到下一行。我已经添加了您的更改,经过多次跟踪和错误,它归结为英特尔 MKL 致命错误:无法加载 mkl_intel_thread.dll。问题是由于没有错误打印,我无法弄清楚要更改什么。一切都很好,现在正在工作。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-01-27
    • 2020-09-22
    • 1970-01-01
    • 1970-01-01
    • 2021-03-26
    • 1970-01-01
    相关资源
    最近更新 更多