在将来的实施中手动轮询流

时间:2019-08-17 12:19:36

标签: asynchronous rust future rust-tokio

我正在迁移到 #question.py class Ui_MainWindow1(object): def setupUi(self, MainWindow): MainWindow.setObjectName("MainWindow") MainWindow.resize(999, 830) self.centralwidget = QtWidgets.QWidget(MainWindow) self.centralwidget.setStyleSheet("font: 75 14pt \"Comic Sans MS\";") self.centralwidget.setObjectName("centralwidget") self.label = QtWidgets.QLabel(self.centralwidget) self.label.setGeometry(QtCore.QRect(330, 10, 151, 31)) self.label.setStyleSheet("background-color: rgb(170, 170, 255);") self.label.setObjectName("label") # continues #function.py from question import Ui_MainWindow1 from PyQt5 import QtWidgets class functions(QtWidgets.QMainWindow , Ui_MainWindow1): def __init__(self): super().__init__() self.setupUi(self ) self.show() #Here are the functions def message(self , messages ): if (len(self.result) > 0): self.questions(categoryname= self.button.text() , id = self.id + 1 , wronganswer = self.wrong_answer , rightanswer = self.right_answer) else: self.msg = QMessageBox.question(self, 'Continue?', 'Do you want to continue the game', QMessageBox.Yes, QMessageBox.No) if (self.msg == QMessageBox.Yes): self.setupUi(self) #Main screen appears but functions do not work #Main Window.py import sys from PyQt5.QtWidgets import QApplication from function import functions app = QApplication(sys.argv) function = functions() sys.exit(app.exec()) 0.3和futures 0.2,并且有一种重复出现的模式我无法重用。我不确定这种模式是否过时,或者是否对tokio做错了。

通常,我有一种类型,可以容纳一个套接字和一些通道接收器。这种结构的Pin实现包括重复轮询流,直到流返回Future(在0.1生态系统中为Pending)。

但是,在期货0.3中,NotReadyFuture::pollStream::poll_next而不是self,这种模式不再起作用:

&mut self

有没有办法修复该代码?如果没有,我可以使用哪种模式来实现相同的逻辑?

1 个答案:

答案 0 :(得分:3)

您可以使用Pin::as_mut来避免消耗Pin

impl MyFuture {
    fn poll_data(self: Pin<&mut Self>, cx: &mut Context) -> Poll<()> {
        use Poll::*;

        let MyFuture {
            ref mut data,
            ref mut state,
            ..
        } = self.get_mut();

        let mut data = Pin::new(data); // Move pin here
        loop {
            match data.as_mut().poll_next(cx) {   // Use in loop by calling `as_mut()`
                Ready(Some(vec)) => state.update(vec),
                Ready(None) => return Ready(()),
                Pending => return Pending,
            }
        }
    }
}

以及将来的隐含内容:

impl Future for MyFuture {
    type Output = ();

    fn poll(mut self: Pin<&mut Self>, cx: &mut Context) -> Poll<Self::Output> {
        use Poll::*;
        // `as_mut()` here to avoid consuming
        if let Ready(_) = self.as_mut().poll_data(cx) { 
            return Ready(());
        }

        // can consume here as this is the last invocation
        if let Ready(_) = self.poll_events(cx) {
            return Ready(());
        }
        return Pending;
    }
}

编辑:

提示:仅在必要时尝试使用Pin。就您而言,您实际上不需要在poll_data函数中使用固定指针。 &mut self很好,可以稍微减少Pin的使用量:

impl MyFuture {
    fn poll_data(&mut self, cx: &mut Context) -> Poll<()> {
        use Poll::*;

        loop {
            match Pin::new(&mut self.data).poll_next(cx) {
                Ready(Some(vec)) => self.state.update(vec),
                Ready(None) => return Ready(()),
                Pending => return Pending,
            }
        }
    }
}

和未来的暗示

impl Future for MyFuture {
    type Output = ();

    fn poll(mut self: Pin<&mut Self>, cx: &mut Context) -> Poll<Self::Output> {
        use Poll::*;
        if let Ready(_) = self.poll_data(cx) {
            return Ready(());
        }

        if let Ready(_) = self.poll_events(cx) {
            return Ready(());
        }
        return Pending;
    }
}