Отрисовка живого графика с PyQtGraph

Не получается отрисовать график в реальном времени через библиотеку PyQtGraph.

Пытался создавать потоки, процессы и так же таймеры, где только можно, но ничего адекватного не получалось, максимум отрисовка графика меняющегося на такой же, без изменения параметров, которые меняются!

Идея заключается в том, что при выполнении функции functional(), которая находится внутри функции methodHookJeeves(), меняется глобальный массив deconvolution[] и при каждом (или несколько) изменений этого массива нужно отрисовывать новый график в виджете graphicsView, тем самым появится анимация, как этот график сходится к графику originalSignal.

Если есть в этом плане преимущество у библиотеки matplotlib, то решение с ним тоже приветствуется. Заранее спасибо!

from PyQt5 import QtCore, QtGui, QtWidgets
from pyqtgraph import PlotWidget
import numpy as np
import pyqtgraph as pg
import random
from multiprocessing import Process
import threading
import time

N = 16
fd = 0.3
impulseResponse = [0]*N
convolution = [0]*N
deconvolution = [0]*N


class Ui_MainWindow(object):
    def setupUi(self, MainWindow):
        MainWindow.setObjectName("MainWindow")
        MainWindow.resize(800, 653)
        self.centralwidget = QtWidgets.QWidget(MainWindow)
        self.centralwidget.setObjectName("centralwidget")
        self.groupBox = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox.setGeometry(QtCore.QRect(10, 10, 191, 571))
        self.groupBox.setObjectName("groupBox")
        self.groupBox_2 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_2.setGeometry(QtCore.QRect(10, 30, 161, 111))
        self.groupBox_2.setObjectName("groupBox_2")
        self.label = QtWidgets.QLabel(self.groupBox_2)
        self.label.setGeometry(QtCore.QRect(10, 16, 47, 20))
        self.label.setObjectName("label")
        self.label_2 = QtWidgets.QLabel(self.groupBox_2)
        self.label_2.setGeometry(QtCore.QRect(10, 50, 47, 16))
        self.label_2.setObjectName("label_2")
        self.label_3 = QtWidgets.QLabel(self.groupBox_2)
        self.label_3.setGeometry(QtCore.QRect(10, 80, 47, 21))
        self.label_3.setObjectName("label_3")
        self.plainTextEdit = QtWidgets.QPlainTextEdit(self.groupBox_2)
        self.plainTextEdit.setGeometry(QtCore.QRect(50, 16, 104, 20))
        self.plainTextEdit.setObjectName("plainTextEdit")
        self.plainTextEdit_2 = QtWidgets.QPlainTextEdit(self.groupBox_2)
        self.plainTextEdit_2.setGeometry(QtCore.QRect(50, 50, 104, 21))
        self.plainTextEdit_2.setObjectName("plainTextEdit_2")
        self.plainTextEdit_3 = QtWidgets.QPlainTextEdit(self.groupBox_2)
        self.plainTextEdit_3.setGeometry(QtCore.QRect(50, 80, 104, 21))
        self.plainTextEdit_3.setObjectName("plainTextEdit_3")
        self.groupBox_5 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_5.setGeometry(QtCore.QRect(10, 390, 161, 91))
        self.groupBox_5.setObjectName("groupBox_5")
        self.plainTextEdit_14 = QtWidgets.QPlainTextEdit(self.groupBox_5)
        self.plainTextEdit_14.setGeometry(QtCore.QRect(50, 60, 104, 21))
        self.plainTextEdit_14.setObjectName("plainTextEdit_14")
        self.label_14 = QtWidgets.QLabel(self.groupBox_5)
        self.label_14.setGeometry(QtCore.QRect(10, 26, 47, 20))
        self.label_14.setObjectName("label_14")
        self.label_13 = QtWidgets.QLabel(self.groupBox_5)
        self.label_13.setGeometry(QtCore.QRect(10, 60, 47, 16))
        self.label_13.setObjectName("label_13")
        self.plainTextEdit_13 = QtWidgets.QPlainTextEdit(self.groupBox_5)
        self.plainTextEdit_13.setGeometry(QtCore.QRect(50, 26, 104, 20))
        self.plainTextEdit_13.setObjectName("plainTextEdit_13")
        self.groupBox_7 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_7.setGeometry(QtCore.QRect(10, 150, 161, 111))
        self.groupBox_7.setObjectName("groupBox_7")
        self.label_7 = QtWidgets.QLabel(self.groupBox_7)
        self.label_7.setGeometry(QtCore.QRect(10, 16, 47, 20))
        self.label_7.setObjectName("label_7")
        self.label_8 = QtWidgets.QLabel(self.groupBox_7)
        self.label_8.setGeometry(QtCore.QRect(10, 50, 47, 16))
        self.label_8.setObjectName("label_8")
        self.label_9 = QtWidgets.QLabel(self.groupBox_7)
        self.label_9.setGeometry(QtCore.QRect(10, 80, 47, 21))
        self.label_9.setObjectName("label_9")
        self.plainTextEdit_7 = QtWidgets.QPlainTextEdit(self.groupBox_7)
        self.plainTextEdit_7.setGeometry(QtCore.QRect(50, 16, 104, 20))
        self.plainTextEdit_7.setObjectName("plainTextEdit_7")
        self.plainTextEdit_8 = QtWidgets.QPlainTextEdit(self.groupBox_7)
        self.plainTextEdit_8.setGeometry(QtCore.QRect(50, 50, 104, 21))
        self.plainTextEdit_8.setObjectName("plainTextEdit_8")
        self.plainTextEdit_9 = QtWidgets.QPlainTextEdit(self.groupBox_7)
        self.plainTextEdit_9.setGeometry(QtCore.QRect(50, 80, 104, 21))
        self.plainTextEdit_9.setObjectName("plainTextEdit_9")
        self.groupBox_3 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_3.setGeometry(QtCore.QRect(10, 270, 161, 111))
        self.groupBox_3.setObjectName("groupBox_3")
        self.label_10 = QtWidgets.QLabel(self.groupBox_3)
        self.label_10.setGeometry(QtCore.QRect(10, 16, 47, 20))
        self.label_10.setObjectName("label_10")
        self.label_11 = QtWidgets.QLabel(self.groupBox_3)
        self.label_11.setGeometry(QtCore.QRect(10, 50, 47, 16))
        self.label_11.setObjectName("label_11")
        self.label_12 = QtWidgets.QLabel(self.groupBox_3)
        self.label_12.setGeometry(QtCore.QRect(10, 80, 47, 21))
        self.label_12.setObjectName("label_12")
        self.plainTextEdit_10 = QtWidgets.QPlainTextEdit(self.groupBox_3)
        self.plainTextEdit_10.setGeometry(QtCore.QRect(50, 16, 104, 20))
        self.plainTextEdit_10.setObjectName("plainTextEdit_10")
        self.plainTextEdit_11 = QtWidgets.QPlainTextEdit(self.groupBox_3)
        self.plainTextEdit_11.setGeometry(QtCore.QRect(50, 50, 104, 21))
        self.plainTextEdit_11.setObjectName("plainTextEdit_11")
        self.plainTextEdit_12 = QtWidgets.QPlainTextEdit(self.groupBox_3)
        self.plainTextEdit_12.setGeometry(QtCore.QRect(50, 80, 104, 21))
        self.plainTextEdit_12.setObjectName("plainTextEdit_12")
        self.groupBox_6 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_6.setGeometry(QtCore.QRect(10, 490, 161, 71))
        self.groupBox_6.setObjectName("groupBox_6")
        self.label_15 = QtWidgets.QLabel(self.groupBox_6)
        self.label_15.setGeometry(QtCore.QRect(10, 20, 71, 16))
        self.label_15.setObjectName("label_15")
        self.plainTextEdit_15 = QtWidgets.QPlainTextEdit(self.groupBox_6)
        self.plainTextEdit_15.setGeometry(QtCore.QRect(90, 20, 61, 21))
        self.plainTextEdit_15.setObjectName("plainTextEdit_15")
        self.label_16 = QtWidgets.QLabel(self.groupBox_6)
        self.label_16.setGeometry(QtCore.QRect(10, 40, 91, 31))
        self.label_16.setObjectName("label_16")
        self.checkBox = QtWidgets.QCheckBox(self.groupBox_6)
        self.checkBox.setGeometry(QtCore.QRect(140, 40, 16, 31))
        self.checkBox.setText("")
        self.checkBox.setObjectName("checkBox")
        self.groupBox_4 = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox_4.setGeometry(QtCore.QRect(210, 10, 581, 241))
        self.groupBox_4.setObjectName("groupBox_4")
        self.graphicsView = PlotWidget(self.groupBox_4)
        self.graphicsView.setGeometry(QtCore.QRect(5, 20, 571, 221))
        self.graphicsView.setObjectName("graphicsView")
        self.groupBox_8 = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox_8.setGeometry(QtCore.QRect(210, 270, 581, 251))
        self.groupBox_8.setObjectName("groupBox_8")
        self.graphicsView_2 = PlotWidget(self.groupBox_8)
        self.graphicsView_2.setGeometry(QtCore.QRect(5, 21, 571, 221))
        self.graphicsView_2.setObjectName("graphicsView_2")
        self.groupBox_9 = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox_9.setGeometry(QtCore.QRect(210, 530, 581, 61))
        self.groupBox_9.setObjectName("groupBox_9")
        self.pushButton = QtWidgets.QPushButton(self.centralwidget)
        self.pushButton.setGeometry(QtCore.QRect(10, 580, 191, 31))
        self.pushButton.setObjectName("pushButton")
        MainWindow.setCentralWidget(self.centralwidget)
        self.menubar = QtWidgets.QMenuBar(MainWindow)
        self.menubar.setGeometry(QtCore.QRect(0, 0, 800, 21))
        self.menubar.setObjectName("menubar")
        MainWindow.setMenuBar(self.menubar)
        self.statusbar = QtWidgets.QStatusBar(MainWindow)
        self.statusbar.setObjectName("statusbar")
        MainWindow.setStatusBar(self.statusbar)

        self.retranslateUi(MainWindow)
        QtCore.QMetaObject.connectSlotsByName(MainWindow)

        self.pushButton.clicked.connect(lambda: self.deconvolutionSignal())

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
        self.groupBox.setTitle(_translate("MainWindow", "Параметры сигнала"))
        self.groupBox_2.setTitle(_translate("MainWindow", "Купол №1"))
        self.label.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit.setPlainText(_translate("MainWindow", "4"))
        self.label_2.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_2.setPlainText(_translate("MainWindow", "4"))
        self.label_3.setText(_translate("MainWindow", "t0 ="))
        self.plainTextEdit_3.setPlainText(_translate("MainWindow", "8"))
        self.groupBox_5.setTitle(_translate(
            "MainWindow", "Импульсная характеристика"))
        self.label_14.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit_13.setPlainText(_translate("MainWindow", "1"))
        self.label_13.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_14.setPlainText(_translate("MainWindow", "3"))
        self.groupBox_7.setTitle(_translate("MainWindow", "Купол №2"))
        self.label_7.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit_7.setPlainText(_translate("MainWindow", "2"))
        self.label_8.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_8.setPlainText(_translate("MainWindow", "3"))
        self.label_9.setText(_translate("MainWindow", "t0 ="))
        self.plainTextEdit_9.setPlainText(_translate("MainWindow", "30"))
        self.groupBox_3.setTitle(_translate("MainWindow", "Купол №3"))
        self.label_10.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit_10.setPlainText(_translate("MainWindow", "3.5"))
        self.label_11.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_11.setPlainText(_translate("MainWindow", "5"))
        self.label_12.setText(_translate("MainWindow", "t0 ="))
        self.plainTextEdit_12.setPlainText(_translate("MainWindow", "60"))
        self.groupBox_6.setTitle(_translate("MainWindow", "Параметры шума"))
        self.label_15.setText(_translate("MainWindow", "Энергия (%):"))
        self.label_16.setText(_translate("MainWindow", "Наложение шума:"))
        self.groupBox_4.setTitle(_translate(
            "MainWindow", "График исходного и восстановленного входных сигналов"))
        self.groupBox_8.setTitle(_translate(
            "MainWindow", "Графики импульсной характеристики и выходного сигнала"))
        self.groupBox_9.setTitle(_translate(
            "MainWindow", "Деконволюция свёртки"))
        self.pushButton.setText(_translate(
            "MainWindow", "Сгенерировать сигнал"))
        self.graphicsView.addLegend()
        self.graphicsView_2.addLegend()

    def gaus(self, i, fd, amplitide, mathExp, variance):
        return amplitide * np.exp(-(pow((i / fd - mathExp), 2) / (2 * pow(variance, 2))))

    def setConvolution(self, originalSignal, impulseResponse, N):
        convolution = [0]*N
        for i in range(0, N):
            convolution[i] = 0
            for j in range(0, N):
                if ((i - j) < 0):
                    convolution[i] += originalSignal[j] * \
                        impulseResponse[i - j + N]
                else:
                    convolution[i] += originalSignal[j] * \
                        impulseResponse[i - j]
        return convolution

    def functional(self, originalSignal, impulseResponse, lambdaList, N):
        global deconvolution
        sum = 0
        for i in range(0, N):
            sum = 0
            for j in range(0, N):
                if ((i - j) < 0):
                    sum += lambdaList[j] * impulseResponse[i - j + N]
                else:
                    sum += lambdaList[j] * impulseResponse[i - j]

            deconvolution[i] = np.exp(-1 - sum)

        valueFunctional = 0
        sum = 0
        for i in range(0, N):
            sum = 0
            for j in range(0, N):
                if ((j - i) < 0):
                    sum += deconvolution[j] * impulseResponse[j - i + N]
                else:
                    sum += deconvolution[j] * impulseResponse[j - i]
            valueFunctional += pow((originalSignal[i] - sum), 2)
        return valueFunctional

    def methodHookJeeves(self, N, beginValue):
        accuracy = 0.000001
        i = 0
        j = 0
        bs = 0
        ps = 0
        Z = 0
        H = 0
        K = 0
        FI = 0
        FB = 0
        B = [0]*N
        Y = [0]*N
        P = [0]*N
        H = 1
        beginValue = []
        beginValue.append(0)
        for i in range(0, N-1):
            beginValue.append(random.randint(0, 32767) / 32767)

        K = H
        for i in range(0, N):
            Y[i] = P[i] = B[i] = beginValue[i]

        FI = self.functional(convolution, impulseResponse, beginValue, N)
        ps = 0
        bs = 1
        FB = FI
        j = 0
        qwerty = 0
        while(True):

            print(qwerty)
            qwerty += 1
            beginValue[j] = Y[j] + K
            Z = self.functional(convolution, impulseResponse, beginValue, N)
            if (Z >= FI):
                beginValue[j] = Y[j] - K
                Z = self.functional(
                    convolution, impulseResponse, beginValue, N)
                if (Z < FI):
                    Y[j] = beginValue[j]
                else:
                    beginValue[j] = Y[j]

            else:
                Y[j] = beginValue[j]

            FI = self.functional(convolution, impulseResponse, beginValue, N)
            if (j < N - 1):
                j = j + 1
                continue

            if (FI + accuracy >= FB):
                if (ps == 1 and bs == 0):
                    for i in range(0, N):
                        P[i] = Y[i] = beginValue[i] = B[i]
                    Z = self.functional(
                        convolution, impulseResponse, beginValue, N)
                    bs = 1
                    ps = 0
                    FI = Z
                    FB = Z
                    j = 0
                    continue
                K /= 10.
                if (K < accuracy):
                    break
                j = 0
                continue

            for i in range(0, N):
                P[i] = 2 * Y[i] - B[i]
                B[i] = Y[i]
                beginValue[i] = P[i]
                Y[i] = beginValue[i]

            Z = self.functional(convolution, impulseResponse, beginValue, N)
            FB = FI
            ps = 1
            bs = 0
            FI = Z
            j = 0

        for i in range(0, N):
            beginValue[i] = P[i]

        B = [0]*N
        Y = [0]*N
        P = [0]*N
        return FB

    def deconvolutionSignal(self):
        global convolution
        global impulseResponse
        global t
        global deconvolution

        self.graphicsView.clear()
        self.graphicsView_2.clear()

        amplitude1 = float(self.plainTextEdit.toPlainText())
        variance1 = float(self.plainTextEdit_2.toPlainText())
        mathExp1 = float(self.plainTextEdit_3.toPlainText())

        amplitude2 = float(self.plainTextEdit_7.toPlainText())
        variance2 = float(self.plainTextEdit_8.toPlainText())
        mathExp2 = float(self.plainTextEdit_9.toPlainText())

        amplitude3 = float(self.plainTextEdit_10.toPlainText())
        variance3 = float(self.plainTextEdit_11.toPlainText())
        mathExp3 = float(self.plainTextEdit_12.toPlainText())

        amplitude4 = float(self.plainTextEdit_13.toPlainText())
        variance4 = float(self.plainTextEdit_14.toPlainText())

        t = []
        for i in range(0, N):
            t.append(i/fd)

        originalSignal = []
        for i in range(0, N):
            originalSignal.append(self.gaus(i, fd, amplitude1, mathExp1, variance1) + self.gaus(i,
                                                                                                fd, amplitude2, mathExp2, variance2) + self.gaus(i, fd, amplitude3, mathExp3, variance3))

        impulseResponse = []
        for i in range(0, 2*N):
            impulseResponse.append(
                self.gaus(i, fd, 1, 0, 5) + self.gaus(i, fd, amplitude4, N / fd, variance4))

        convolution = self.setConvolution(originalSignal, impulseResponse, N)

        lambdaList = []
        for i in range(0, N):
            lambdaList.append(0)

        self.methodHookJeeves(N, lambdaList)

        self.graphicsView.plot(
            t, originalSignal, pen='r', name='Исходный сигнал')
        self.graphicsView.plot(t, deconvolution, pen='b',
                               name='Восстановленный сигнал')
        self.graphicsView_2.plot(
            t, convolution, pen='y', name='Выходной сигнал после свёртки')

        originalSignal = [0]*N
        impulseResponse = [0]*N
        lambdaList = [0]*N


if __name__ == "__main__":
    import sys
    app = QtWidgets.QApplication(sys.argv)
    MainWindow = QtWidgets.QMainWindow()
    ui = Ui_MainWindow()
    ui.setupUi(MainWindow)
    MainWindow.show()
    MainWindow.setWindowTitle(
        'Деконволюция свёртки методом максимума энтропии')
    MainWindow.setGeometry(280, 60, 800, 653)
    sys.exit(app.exec_())

Загрузил код на гитхаб, с картинкой (stackoverflow не даёт загрузить). https://github.com/turkin812/DeconvolutionSignal


Ответы (1 шт):

Автор решения: S. Nick

НИКОГДА НЕ ИЗМЕНЯЙТЕ код, сгенерированный Qt Designer, НИКОГДА.
Создайте другой класс, который наследуется от соответствующего виджета, и используйте созданный класс для его заполнения.

Почему глобальные переменные - зло?

Класс QDoubleSpinBox предоставляет виджет счетчика, который принимает двойные значения. Виджет QPlainTextEdit предназначен для других целей.

Если возможно делать несколько операций в одном цикле, то и делать их надо в одном цикле, а не разбивать на несколько абсолютно одинаковых циклов.

Я не проверял что делает ваша логика расчетов, а только упорядочил ваш код с учетом вышесказанного и оставил некоторые пометки, чтобы вы видели чего я касался.

Просто скопируйте мой пример, запустите и нажимайте на кнопки. Потом строчка за строчкой посмотрите что я поменял. Пробуйте.

import random
# ??? import time
# ??? import threading
# ??? from multiprocessing import Process
import numpy as np

from PyQt5 import QtCore, QtGui, QtWidgets

import pyqtgraph as pg
from pyqtgraph import PlotWidget

'''
N = 16
fd = 0.3
impulseResponse = [0]*N
convolution = [0]*N
deconvolution = [0]*N
'''

class Ui_MainWindow(object):
    def setupUi(self, MainWindow):
        MainWindow.setObjectName("MainWindow")
        MainWindow.resize(800, 653)
        self.centralwidget = QtWidgets.QWidget(MainWindow)
        self.centralwidget.setObjectName("centralwidget")
        
        self.groupBox = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox.setGeometry(QtCore.QRect(10, 10, 191, 571))
        self.groupBox.setObjectName("groupBox")
        
        self.groupBox_2 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_2.setGeometry(QtCore.QRect(10, 30, 161, 111))
        self.groupBox_2.setObjectName("groupBox_2")
        self.label = QtWidgets.QLabel(self.groupBox_2)
        self.label.setGeometry(QtCore.QRect(10, 16, 47, 20))
        self.label.setObjectName("label")
        self.label_2 = QtWidgets.QLabel(self.groupBox_2)
        self.label_2.setGeometry(QtCore.QRect(10, 50, 47, 16))
        self.label_2.setObjectName("label_2")
        self.label_3 = QtWidgets.QLabel(self.groupBox_2)
        self.label_3.setGeometry(QtCore.QRect(10, 80, 47, 21))
        self.label_3.setObjectName("label_3")
# ???
#        self.plainTextEdit = QtWidgets.QPlainTextEdit(self.groupBox_2)
        self.plainTextEdit = QtWidgets.QDoubleSpinBox(self.groupBox_2)
        self.plainTextEdit.setDecimals(2)         
        self.plainTextEdit.setGeometry(QtCore.QRect(50, 16, 104, 20))
        self.plainTextEdit.setObjectName("plainTextEdit")
# ???
        self.plainTextEdit_2 = QtWidgets.QDoubleSpinBox(self.groupBox_2)
        self.plainTextEdit_2.setDecimals(2)
        self.plainTextEdit_2.setGeometry(QtCore.QRect(50, 50, 104, 21))
        self.plainTextEdit_2.setObjectName("plainTextEdit_2")
# ???
        self.plainTextEdit_3 = QtWidgets.QDoubleSpinBox(self.groupBox_2)
        self.plainTextEdit_3.setDecimals(2)
        self.plainTextEdit_3.setGeometry(QtCore.QRect(50, 80, 104, 21))
        self.plainTextEdit_3.setObjectName("plainTextEdit_3")
        
        self.groupBox_5 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_5.setGeometry(QtCore.QRect(10, 390, 161, 91))
        self.groupBox_5.setObjectName("groupBox_5")
# ???
        self.plainTextEdit_14 = QtWidgets.QDoubleSpinBox(self.groupBox_5)
        self.plainTextEdit_14.setDecimals(2)
        self.plainTextEdit_14.setGeometry(QtCore.QRect(50, 60, 104, 21))
        self.plainTextEdit_14.setObjectName("plainTextEdit_14")
        self.label_14 = QtWidgets.QLabel(self.groupBox_5)
        self.label_14.setGeometry(QtCore.QRect(10, 26, 47, 20))
        self.label_14.setObjectName("label_14")
        self.label_13 = QtWidgets.QLabel(self.groupBox_5)
        self.label_13.setGeometry(QtCore.QRect(10, 60, 47, 16))
        self.label_13.setObjectName("label_13")
# ???
        self.plainTextEdit_13 = QtWidgets.QDoubleSpinBox(self.groupBox_5)
        self.plainTextEdit_13.setDecimals(2)
        self.plainTextEdit_13.setGeometry(QtCore.QRect(50, 26, 104, 20))
        self.plainTextEdit_13.setObjectName("plainTextEdit_13")
        
        self.groupBox_7 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_7.setGeometry(QtCore.QRect(10, 150, 161, 111))
        self.groupBox_7.setObjectName("groupBox_7")
        self.label_7 = QtWidgets.QLabel(self.groupBox_7)
        self.label_7.setGeometry(QtCore.QRect(10, 16, 47, 20))
        self.label_7.setObjectName("label_7")
        self.label_8 = QtWidgets.QLabel(self.groupBox_7)
        self.label_8.setGeometry(QtCore.QRect(10, 50, 47, 16))
        self.label_8.setObjectName("label_8")
        self.label_9 = QtWidgets.QLabel(self.groupBox_7)
        self.label_9.setGeometry(QtCore.QRect(10, 80, 47, 21))
        self.label_9.setObjectName("label_9")
# ???
        self.plainTextEdit_7 = QtWidgets.QDoubleSpinBox(self.groupBox_7)
        self.plainTextEdit_7.setDecimals(2)
        self.plainTextEdit_7.setGeometry(QtCore.QRect(50, 16, 104, 20))
        self.plainTextEdit_7.setObjectName("plainTextEdit_7")
# ???
        self.plainTextEdit_8 = QtWidgets.QDoubleSpinBox(self.groupBox_7)
        self.plainTextEdit_8.setDecimals(2)
        self.plainTextEdit_8.setGeometry(QtCore.QRect(50, 50, 104, 21))
        self.plainTextEdit_8.setObjectName("plainTextEdit_8")
# ???
        self.plainTextEdit_9 = QtWidgets.QDoubleSpinBox(self.groupBox_7)
        self.plainTextEdit_9.setDecimals(2)
        self.plainTextEdit_9.setGeometry(QtCore.QRect(50, 80, 104, 21))
        self.plainTextEdit_9.setObjectName("plainTextEdit_9")
# ???
        self.groupBox_3 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_3.setGeometry(QtCore.QRect(10, 270, 161, 111))
        self.groupBox_3.setObjectName("groupBox_3")
        self.label_10 = QtWidgets.QLabel(self.groupBox_3)
        self.label_10.setGeometry(QtCore.QRect(10, 16, 47, 20))
        self.label_10.setObjectName("label_10")
        self.label_11 = QtWidgets.QLabel(self.groupBox_3)
        self.label_11.setGeometry(QtCore.QRect(10, 50, 47, 16))
        self.label_11.setObjectName("label_11")
        self.label_12 = QtWidgets.QLabel(self.groupBox_3)
        self.label_12.setGeometry(QtCore.QRect(10, 80, 47, 21))
        self.label_12.setObjectName("label_12")
# ???
        self.plainTextEdit_10 = QtWidgets.QDoubleSpinBox(self.groupBox_3)
        self.plainTextEdit_10.setDecimals(2)
        self.plainTextEdit_10.setGeometry(QtCore.QRect(50, 16, 104, 20))
        self.plainTextEdit_10.setObjectName("plainTextEdit_10")
# ???
        self.plainTextEdit_11 = QtWidgets.QDoubleSpinBox(self.groupBox_3)
        self.plainTextEdit_11.setDecimals(2)
        self.plainTextEdit_11.setGeometry(QtCore.QRect(50, 50, 104, 21))
        self.plainTextEdit_11.setObjectName("plainTextEdit_11")
# ???
        self.plainTextEdit_12 = QtWidgets.QDoubleSpinBox(self.groupBox_3)
        self.plainTextEdit_12.setDecimals(2)
        self.plainTextEdit_12.setGeometry(QtCore.QRect(50, 80, 104, 21))
        self.plainTextEdit_12.setObjectName("plainTextEdit_12")
        self.groupBox_6 = QtWidgets.QGroupBox(self.groupBox)
        self.groupBox_6.setGeometry(QtCore.QRect(10, 490, 161, 71))
        self.groupBox_6.setObjectName("groupBox_6")
        self.label_15 = QtWidgets.QLabel(self.groupBox_6)
        self.label_15.setGeometry(QtCore.QRect(10, 20, 71, 16))
        self.label_15.setObjectName("label_15")
# ???
        self.plainTextEdit_15 = QtWidgets.QDoubleSpinBox(self.groupBox_6)
        self.plainTextEdit_15.setDecimals(2)
        self.plainTextEdit_15.setGeometry(QtCore.QRect(90, 20, 61, 21))
        self.plainTextEdit_15.setObjectName("plainTextEdit_15")
        self.label_16 = QtWidgets.QLabel(self.groupBox_6)
        self.label_16.setGeometry(QtCore.QRect(10, 40, 91, 31))
        self.label_16.setObjectName("label_16")
        self.checkBox = QtWidgets.QCheckBox(self.groupBox_6)
        self.checkBox.setGeometry(QtCore.QRect(140, 40, 16, 31))
        self.checkBox.setText("")
        self.checkBox.setObjectName("checkBox")
        self.groupBox_4 = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox_4.setGeometry(QtCore.QRect(210, 10, 581, 241))
        self.groupBox_4.setObjectName("groupBox_4")
        self.graphicsView = PlotWidget(self.groupBox_4)
        self.graphicsView.setGeometry(QtCore.QRect(5, 20, 571, 221))
        self.graphicsView.setObjectName("graphicsView")
        self.groupBox_8 = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox_8.setGeometry(QtCore.QRect(210, 270, 581, 251))
        self.groupBox_8.setObjectName("groupBox_8")
        self.graphicsView_2 = PlotWidget(self.groupBox_8)
        self.graphicsView_2.setGeometry(QtCore.QRect(5, 21, 571, 221))
        self.graphicsView_2.setObjectName("graphicsView_2")
        self.groupBox_9 = QtWidgets.QGroupBox(self.centralwidget)
        self.groupBox_9.setGeometry(QtCore.QRect(210, 530, 581, 61))
        self.groupBox_9.setObjectName("groupBox_9")
        self.pushButton = QtWidgets.QPushButton(self.centralwidget)
        self.pushButton.setGeometry(QtCore.QRect(10, 580, 191, 31))
        self.pushButton.setObjectName("pushButton")
        MainWindow.setCentralWidget(self.centralwidget)
        self.menubar = QtWidgets.QMenuBar(MainWindow)
        self.menubar.setGeometry(QtCore.QRect(0, 0, 800, 21))
        self.menubar.setObjectName("menubar")
        MainWindow.setMenuBar(self.menubar)
        self.statusbar = QtWidgets.QStatusBar(MainWindow)
        self.statusbar.setObjectName("statusbar")
        MainWindow.setStatusBar(self.statusbar)

        self.retranslateUi(MainWindow)
        QtCore.QMetaObject.connectSlotsByName(MainWindow)

#        self.pushButton.clicked.connect(lambda: self.deconvolutionSignal())

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
        self.groupBox.setTitle(_translate("MainWindow", "Параметры сигнала"))
        self.groupBox_2.setTitle(_translate("MainWindow", "Купол №1"))
        self.label.setText(_translate("MainWindow", "A ="))
        
#        self.plainTextEdit.setPlainText(_translate("MainWindow", "4"))
        self.plainTextEdit.setValue(4)                                              # +++ ...
        
        self.label_2.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_2.setValue(4)
        self.label_3.setText(_translate("MainWindow", "t0 ="))
        self.plainTextEdit_3.setValue(8)
        self.groupBox_5.setTitle(_translate(
            "MainWindow", "Импульсная характеристика"))
        self.label_14.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit_13.setValue(1)
        self.label_13.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_14.setValue(3)
        self.groupBox_7.setTitle(_translate("MainWindow", "Купол №2"))
        self.label_7.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit_7.setValue(2)
        self.label_8.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_8.setValue(3)
        self.label_9.setText(_translate("MainWindow", "t0 ="))
        self.plainTextEdit_9.setValue(30)
        self.groupBox_3.setTitle(_translate("MainWindow", "Купол №3"))
        self.label_10.setText(_translate("MainWindow", "A ="))
        self.plainTextEdit_10.setValue(3.5)
        self.label_11.setText(_translate("MainWindow", "σ ="))
        self.plainTextEdit_11.setValue(5)
        self.label_12.setText(_translate("MainWindow", "t0 ="))
        self.plainTextEdit_12.setValue(60)
        self.groupBox_6.setTitle(_translate("MainWindow", "Параметры шума"))
        self.label_15.setText(_translate("MainWindow", "Энергия (%):"))
        self.label_16.setText(_translate("MainWindow", "Наложение шума:"))
        self.groupBox_4.setTitle(_translate(
            "MainWindow", "График исходного и восстановленного входных сигналов"))
        self.groupBox_8.setTitle(_translate(
            "MainWindow", "Графики импульсной характеристики и выходного сигнала"))
        self.groupBox_9.setTitle(_translate(
            "MainWindow", "Деконволюция свёртки"))
        self.pushButton.setText(_translate(
            "MainWindow", "Сгенерировать сигнал"))
            
#         self.graphicsView.addLegend()
#         self.graphicsView_2.addLegend()


class MainWindow(QtWidgets.QMainWindow, Ui_MainWindow):
    N = 16                                                                # +++
    fd = 0.3                                                              # +++
    impulseResponse = [0]*N                                               # +++
    convolution = [0]*N                                                   # +++
    deconvolution = [0]*N                                                 # +++

    def __init__(self):
        super().__init__()
        
        self.setupUi(self)

#        self.pushButton.clicked.connect(lambda: self.deconvolutionSignal())
        self.pushButton.clicked.connect(self.deconvolutionSignal)

    def gaus(self, i, fd, amplitide, mathExp, variance):
        return amplitide * np.exp(-(pow((i / fd - mathExp), 2) / (2 * pow(variance, 2))))

    def setConvolution(self, originalSignal, impulseResponse, N):
        self.convolution = [0]*N
        for i in range(0, N):
            self.convolution[i] = 0
            for j in range(0, N):
                if ((i - j) < 0):
                    self.convolution[i] += originalSignal[j] * \
                        impulseResponse[i - j + N]
                else:
                    self.convolution[i] += originalSignal[j] * \
                        impulseResponse[i - j]
        return self.convolution

    def functional(self, originalSignal, impulseResponse, lambdaList, N):
#        global deconvolution
        sum = 0
        for i in range(0, N):
            sum = 0
            for j in range(0, N):
                if ((i - j) < 0):
                    sum += lambdaList[j] * impulseResponse[i - j + N]
                else:
                    sum += lambdaList[j] * impulseResponse[i - j]

            self.deconvolution[i] = np.exp(-1 - sum)

        valueFunctional = 0
        sum = 0
        for i in range(0, N):
            sum = 0
            for j in range(0, N):
                if ((j - i) < 0):
                    sum += self.deconvolution[j] * impulseResponse[j - i + N]
                else:
                    sum += self.deconvolution[j] * impulseResponse[j - i]
            valueFunctional += pow((originalSignal[i] - sum), 2)


# Управление событиями. Почитаете для чего это можно использовать               
        QtWidgets.QApplication.processEvents()                      # +++   
        
        return valueFunctional


    def methodHookJeeves(self, N, beginValue):
# зачем вам такая точность ???    
#        accuracy = 0.000001
        accuracy = 0.01                    # +++ 0.01

        i = 0
        j = 0
        bs = 0
        ps = 0
        Z = 0
        H = 0
        K = 0
        FI = 0
        FB = 0
        B = [0]*N
        Y = [0]*N
        P = [0]*N
        H = 1
        beginValue = []
        beginValue.append(0)
        for i in range(0, N-1):
            beginValue.append(random.randint(0, 32767) / 32767)

        K = H
        for i in range(0, N):
            Y[i] = P[i] = B[i] = beginValue[i]
#
        FI = self.functional(self.convolution, self.impulseResponse, beginValue, N)
        FI = round(FI, 2)                # я не знаю зачем вам такая точность? - уменьшил до 2
        ps = 0
        bs = 1
        FB = FI
        j = 0
        qwerty = 0

        
        while(True):
# ???
#            print(qwerty)
            if not qwerty % 5000:
                print('---------------------------', qwerty)
            
            
            qwerty += 1
            beginValue[j] = Y[j] + K
#             
            Z = self.functional(self.convolution, self.impulseResponse, beginValue, N)
            Z = round(Z, 2)                # я не знаю зачем вам такая точность? - уменьшил до 2

            if (Z >= FI):
                beginValue[j] = Y[j] - K
                Z = self.functional(
                    self.convolution, self.impulseResponse, beginValue, N)
                Z = round(Z, 2)                # я не знаю зачем вам такая точность? - уменьшил до 2
                if (Z < FI):
                    Y[j] = beginValue[j]
                else:
                    beginValue[j] = Y[j]
            else:
                Y[j] = beginValue[j]

            FI = self.functional(self.convolution, self.impulseResponse, beginValue, N)
            FI = round(FI, 2)                # я не знаю зачем вам такая точность? - уменьшил до 2
            if (j < N - 1):
                j = j + 1
                continue

            if (FI + accuracy >= FB):
                if (ps == 1 and bs == 0):
                    for i in range(0, N):
                        P[i] = Y[i] = beginValue[i] = B[i]
                    Z = self.functional(
                        self.convolution, self.impulseResponse, beginValue, N)
                    Z = round(Z, 2)                # я не знаю зачем вам такая точность? - уменьшил до 2    
                    bs = 1
                    ps = 0
                    FI = Z
                    FB = Z
                    j = 0
                    continue
                K /= 10.
                if (K < accuracy):
                    print(f'====== K = {K} < accuracy = {accuracy}') # 
                    break
                j = 0
                continue

            for i in range(0, N):
                P[i] = 2 * Y[i] - B[i]
                B[i] = Y[i]
                beginValue[i] = P[i]
                Y[i] = beginValue[i]

            Z = self.functional(self.convolution, self.impulseResponse, beginValue, N)
            Z = round(Z, 2)                # я не знаю зачем вам такая точность? - уменьшил до 2
            FB = FI
            ps = 1
            bs = 0
            FI = Z
            j = 0

        for i in range(0, N):
            beginValue[i] = P[i]

        B = [0]*N
        Y = [0]*N
        P = [0]*N
        return FB

    def deconvolutionSignal(self):
#        global convolution
#        global impulseResponse
#        global t
#        global deconvolution
#        self.graphicsView.clear()
#        self.graphicsView_2.clear()

#        amplitude1 = float(self.plainTextEdit.toPlainText())
        amplitude1 = self.plainTextEdit.value()                        # !!! +++ ...

        variance1 = self.plainTextEdit_2.value()
        mathExp1 = self.plainTextEdit_3.value()

        amplitude2 = self.plainTextEdit_7.value()
        variance2 = self.plainTextEdit_8.value()
        mathExp2 = self.plainTextEdit_9.value()

        amplitude3 = self.plainTextEdit_10.value()
        variance3 = self.plainTextEdit_11.value()
        mathExp3 = self.plainTextEdit_12.value()

        amplitude4 = self.plainTextEdit_13.value()
        variance4 = self.plainTextEdit_14.value()

        t = []
        originalSignal = []                         # 
        lambdaList = []
        for i in range(0, self.N):
            t.append(i / self.fd)

#        originalSignal = []
#        for i in range(0, self.N):
            # !!! +++ это делается в одном цикле
            originalSignal.append(self.gaus(i, self.fd, amplitude1, mathExp1, variance1) + self.gaus(
                i, self.fd, amplitude2, mathExp2, variance2) + self.gaus(i, self.fd, amplitude3, mathExp3, variance3))
            lambdaList.append(0)

        self.impulseResponse = []
        for i in range(0, 2 * self.N):
            self.impulseResponse.append(
                self.gaus(i, self.fd, 1, 0, 5) + self.gaus(i, self.fd, amplitude4, self.N / self.fd, variance4))

        self.convolution = self.setConvolution(originalSignal, self.impulseResponse, self.N)

#        lambdaList = []
#        for i in range(0, self.N):
#            lambdaList.append(0)
        
# 
        self.methodHookJeeves(self.N, lambdaList)
        
        self.graphicsView.clear()
        self.graphicsView.plot(
            t, originalSignal, pen='r', name='Исходный сигнал')
            
        self.graphicsView.plot(
            t, self.deconvolution, pen='b', name='Восстановленный сигнал')
            
        self.graphicsView_2.clear()   
        self.graphicsView_2.plot(
            t, self.convolution, pen='y', name='Выходной сигнал после свёртки')

# ???
        originalSignal = [0]*self.N
        self.impulseResponse = [0]*self.N
        lambdaList = [0]*self.N

        

if __name__ == "__main__":
    import sys
    app = QtWidgets.QApplication(sys.argv)
    w = MainWindow()
    w.setWindowTitle(
        'Деконволюция свёртки методом максимума энтропии')
    w.resize(800, 630)
    w.show()    
    sys.exit(app.exec_())

введите сюда описание изображения

→ Ссылка