Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. International
  3. India
  4. Problem for slow operations in Qt program
Forum Update on Monday, May 27th 2025

Problem for slow operations in Qt program

Scheduled Pinned Locked Moved India
26 Posts 8 Posters 14.3k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • M Offline
    M Offline
    maxoreli
    wrote on 22 Jun 2011, 13:13 last edited by
    #5

    I'm trying use Qthread ,but running of my program dont start.
    this is class of my object
    @
    #include "formdp0j_poj.h"
    #include "forms0ixmij_x_q0ij.h"
    #include "forms1ixmij_x_q1ij.h"
    #include "forms2ixmij_x_q2ij.h"
    #include"mythread.h"

    FormdP0j_Poj::FormdP0j_Poj(QWidget *parent) :
    QWidget(parent)
    {
    setupUi(this);
    table=new QTableWidget;
    table->setRowCount(5);
    table->setColumnCount(40);
    setupContents();
    calculate();
    }

    void FormdP0j_Poj::changeEvent(QEvent *e)
    {
    QWidget::changeEvent(e);
    switch (e->type()) {
    case QEvent::LanguageChange:
    retranslateUi(this);
    break;
    default:
    break;
    }
    }

    void FormdP0j_Poj::setupContents()
    {

    //in the constructor's widget,i m doing long operations too
    FormS0ixmij_x_q0ij *matrixS0ixmij_x_q0ij=new FormS0ixmij_x_q0ij;

    FormS1ixmij_x_q1ij *matrixS1ixmij_x_q1ij=new FormS1ixmij_x_q1ij;

    FormS2ixmij_x_q2ij *matrixS2ixmij_x_q2ij=new FormS2ixmij_x_q2ij;

    tempS0ixmij_x_q0ij= matrixS0ixmij_x_q0ij->getTable();
    

    tempS1ixmij_x_q1ij= matrixS1ixmij_x_q1ij->getTable();
    tempS2ixmij_x_q2ij= matrixS2ixmij_x_q2ij->getTable();

    QVariant variant;
    QTableWidgetItem * curItem=new QTableWidgetItem;
    
    
    if(  (tempS0ixmij_x_q0ij!=0)   &&  (tempS1ixmij_x_q1ij !=0 ) &&  (tempS2ixmij_x_q2ij !=0) ){
    
    
        //copie de l'entete
        int c=1;
        table->setItem(1,0,new QTableWidgetItem(QString("dP0j/P0j")));
        table->setItem(2,0,new QTableWidgetItem(QString("dP1j/P1j")));
        table->setItem(3,0,new QTableWidgetItem(QString("dP2j/P2j")));
        //table->setItem(4,0,new QTableWidgetItem(QString("q")));
    
        for(int j=1; j < tempS0ixmij_x_q0ij->columnCount()  ;j=j+1)
        {
            curItem=new QTableWidgetItem;
            variant= tempS0ixmij_x_q0ij->item(0,j)->data(0);
            curItem->setData(0,variant);
            table->setItem(0,c,curItem);
            c=c+1;
        }
    
    
        //1ere ligne
        double coef,a,b;
        int RCount=tempS0ixmij_x_q0ij->rowCount();
        int CCount=tempS0ixmij_x_q0ij->columnCount(); 
         QTableWidgetItem * curItem=new QTableWidgetItem;
    
        for( int j =1; j <  CCount ;j=j+1 
        {
            c=1; coef=0.;
            for( int i=1 ; j < RCount  ;i=i+1 )
            {
               if ((tempS0ixmij_x_q0ij->item(i,j) !=0)){
    
                   a= (tempS0ixmij_x_q0ij->item(i,j)->data(0).toDouble());
                   coef= coef + a;
                }
    
            }
           curItem=new QTableWidgetItem;
            curItem->setData(0,coef);
           table->setItem(1,c,curItem);
            c=c+1;
            QCoreApplication::processEvents();
        }
    
    
        table->resizeColumnsToContents();
        table->resizeRowsToContents();
        horizontalLayout->addWidget(table);
    }
    

    }

    void FormdP0j_Poj::calculate()
    {
    //calcul des coefficients

    //2 ligne
    for( int j =1; j < tempS1ixmij_x_q1ij->columnCount() ;j=j+1 )
    {
        c=1; coef=0.;
        for( int i=1 ; j < tempS1ixmij_x_q1ij->rowCount()  ;i=i+1 )
        {
            if ((tempS1ixmij_x_q1ij->item(i,j) !=0)){
    
                a=tempS1ixmij_x_q1ij->item(i,j)->data(0).toDouble();
                coef= coef + a;
            }
    
        }
        curItem=new QTableWidgetItem;
        curItem->setData(0,coef);
        table->setItem(2,c,curItem);
        c=c+1;
       // QCoreApplication::processEvents();
    }
    
    
    //3 ligne
    for( int j =1; j < tempS1ixmij_x_q1ij->columnCount() ;j=j+1 )
    {
        c=1; coef=0.;
        for( int i=1 ; j < tempS1ixmij_x_q1ij->rowCount()  ;i=i+1 )
        {
            if ((tempS2ixmij_x_q2ij->item(i,j) !=0)){
    
                a=tempS2ixmij_x_q2ij->item(i,j)->data(0).toDouble();
                coef= coef + a;
            }
    
        }
        curItem=new QTableWidgetItem;
        curItem->setData(0,coef);
        table->setItem(3,c,curItem);
        c=c+1;
    
    }
    

    }
    @

    and after i 'm calling my widget in a mainwindow's slot
    @
    void MainWindow::on_actionDP0j_Poj_dP2j_P2j_triggered()
    {

    FormdP0j_Poj *w=new  FormdP0j_Poj;
    int indexNouvelOnglet = onglets->addTab(createPageOnglet(w), tr("Matrix(dP0j/P0j à dP2j/P2j"));
    onglets->setCurrentIndex(indexNouvelOnglet);
    

    }
    @
    and the main
    @
    #include "mainwindow.h"
    #include<QPushButton>

    int main(int argc, char *argv[])
    {
    QApplication a(argc, argv);

      MainWindow *mainw=new MainWindow;
      mainw->show();
    
    
    return a.exec&#40;&#41;;
    

    }
    @
    so ,when i run, program dont respond.
    Thanks for advance

    1 Reply Last reply
    0
    • M Offline
      M Offline
      mlong
      wrote on 24 Jun 2011, 21:17 last edited by
      #6

      Where are you using a threads? It's hard to tell from the code you posted.

      Edit: Also, remember, GUI elements (widgets) cannot be in any other thread except the main thread.

      Software Engineer
      My views and opinions do not necessarily reflect those of anyone -- living or dead, real or fictional -- in this universe or any other similar multiverse node. Void where prohibited. Your mileage may vary. Caveat emptor.

      1 Reply Last reply
      0
      • D Offline
        D Offline
        deimos
        wrote on 24 Jun 2011, 22:13 last edited by
        #7

        I never tried and don't know it is the right way to go on, but a shortcut to this problem could be put this

        @QTimer::singleShot(100, this, setupContents());@

        in your constructor. You will need to define setupContents() as a slots and then call calculate(); at the end of setupContents() function.

        1 Reply Last reply
        0
        • M Offline
          M Offline
          maxoreli
          wrote on 25 Jun 2011, 10:55 last edited by
          #8

          Ok,i know, i dont put in this code, but how do I use QThread, for speed up my program .
          Please explain me or give an sample of code.
          Thanks for advance.

          [quote author="mlong" date="1308950226"]Where are you using a threads? It's hard to tell from the code you posted.

          Edit: Also, remember, GUI elements (widgets) cannot be in any other thread except the main thread.
          [/quote]

          1 Reply Last reply
          0
          • T Offline
            T Offline
            TobbY
            wrote on 25 Jun 2011, 11:05 last edited by
            #9

            is using threads speed up program????

            1 Reply Last reply
            0
            • M Offline
              M Offline
              maxoreli
              wrote on 25 Jun 2011, 11:17 last edited by
              #10

              [quote author="TobbY" date="1308999921"]is using threads speed up program????[/quote]
              Please help me,I have already documentationon Qthread, i dont know how to apply that, please show me how do this and give a sample of code.
              Thanks for advance.

              1 Reply Last reply
              0
              • M Offline
                M Offline
                maxoreli
                wrote on 25 Jun 2011, 15:42 last edited by
                #11

                [quote author="marcoB" date="1308953599"]I never tried and don't know it is the right way to go on, but a shortcut to this problem could be put this

                @QTimer::singleShot(100, this, setupContents());@

                in your constructor. You will need to define setupContents() as a slots and then call calculate(); at the end of setupContents() function. [/quote]

                [quote author="marcoB" date="1308953599"]I never tried and don't know it is the right way to go on, but a shortcut to this problem could be put this

                @QTimer::singleShot(100, this, setupContents());@

                in your constructor. You will need to define setupContents() as a slots and then call calculate(); at the end of setupContents() function. [/quote]

                I'm trying that,but i have same problems

                1 Reply Last reply
                0
                • S Offline
                  S Offline
                  Santosh Reddy
                  wrote on 25 Jun 2011, 21:55 last edited by
                  #12

                  [quote author="maxoreli" date="1309016523"]
                  [quote author="marcoB" date="1308953599"]I never tried and don't know it is the right way to go on, but a shortcut to this problem could be put this

                  @QTimer::singleShot(100, this, setupContents());@

                  in your constructor. You will need to define setupContents() as a slots and then call calculate(); at the end of setupContents() function. [/quote]

                  [quote author="marcoB" date="1308953599"]I never tried and don't know it is the right way to go on, but a shortcut to this problem could be put this

                  @QTimer::singleShot(100, this, setupContents());@

                  in your constructor. You will need to define setupContents() as a slots and then call calculate(); at the end of setupContents() function. [/quote]

                  I'm trying that,but i have same problems

                  [/quote]

                  What is the problem ?

                  You can add QProgressBar, to indicate the status of setupContents()

                  SS

                  1 Reply Last reply
                  0
                  • D Offline
                    D Offline
                    deimos
                    wrote on 25 Jun 2011, 22:46 last edited by
                    #13

                    After singleShot call, your GUI should respond to user, even if I noticed now you put some

                    @QCoreApplication::processEvents();@

                    in your loops and that could be enough to achieve what you are looking for.
                    Has Santosh sayd, try to put a progressBar in your form, it should works

                    1 Reply Last reply
                    0
                    • A Offline
                      A Offline
                      andre
                      wrote on 26 Jun 2011, 06:48 last edited by
                      #14

                      I find that progressEvents, especially the call without any arguments, is a road to very hard to debug issues. I try to avoid it.

                      1 Reply Last reply
                      0
                      • M Offline
                        M Offline
                        maxoreli
                        wrote on 26 Jun 2011, 06:58 last edited by
                        #15

                        Hello,Andre please I have difficulty to apply what you saw in your first reply.
                        Please ,read my code and give an sample of code and how do I do it(speed up my program)
                        Thanks for advance.

                        [quote author="Andre" date="1309070939"]I find that progressEvents, especially the call without any arguments, is a road to very hard to debug issues. I try to avoid it. [/quote]

                        1 Reply Last reply
                        0
                        • A Offline
                          A Offline
                          andre
                          wrote on 26 Jun 2011, 10:32 last edited by
                          #16

                          In the code you posted, you are not using threads; at least not where we can see them.

                          Your main issue is, that you are starting your intensive code from the constructor of your form. As you have been told before, you should not do that. Instead, you could re-write your constructor to something like this:

                          @
                          FormdP0j_Poj::FormdP0j_Poj(QWidget *parent) :
                          QWidget(parent)
                          {
                          setupUi(this);
                          table=new QTableWidget;
                          table->setRowCount(5);
                          table->setColumnCount(40);
                          // trigger heavy work to be done in a little while
                          QTimer::singleShot(100, this, SLOT(startHeavyWork()));
                          }

                          //this needs to be a slot in your declaration
                          FormdP0j_Poj::startHeavyWork()
                          {
                          setupContents();
                          calculate();
                          }
                          @

                          That should at least get your form displayed properly, if not responding well yet.

                          I am guessing your calculate function may take quite a bit of time, right? Assuming that it is indeed this function that takes most time (and not the setupContents function), let's continue our optimization:

                          So, the calculate function is a candidate to make run asynchronous. That is: it running should not block your GUI. One problem is, is that your current function will impact the GUI (it creates QTableWidgetItems), and is thus not suited to put in a thread. Doing things in your GUI from another thread is not allowed. Lucky for you, the calculate function is an easy candidate to chop into pieces that can be run one after another, and return to the main loop in between.

                          How you make the split in blocks exactly, depends on your problem. It might take some experimentation. I have no idea how big the data sets you are working with are, and how much time each iteration may take. My goal would be to make sure you return to the eventloop at least 24 times per second, but again: some experimentation would be needed.

                          Lets start by re-arranging your calculation a bit: you are looping over the exact same two data structures in both the blocks of your calculation. That is a waste of time. Instead, loop over them only one time, and perform both calculations in one go:

                          @
                          //calculation, version 2
                          void FormdP0j_Poj::calculate()
                          {
                          //calcul des coefficients

                          // you seem to be missing some variable declarations. Did you cut those out?

                          //2 ligne
                          for( int j =1; j < tempS1ixmij_x_q1ij->columnCount() ;j=j+1 )
                          {
                              c=1; coef=0.; //where are these declared?
                              for( int i=1 ; j < tempS1ixmij_x_q1ij->rowCount()  ;i=i+1 )
                              {
                                  if ((tempS1ixmij_x_q1ij->item(i,j) !=0)){
                          
                                      a=tempS1ixmij_x_q1ij->item(i,j)->data(0).toDouble();
                                      coef= coef + a;
                                  }
                          
                                  if ((tempS2ixmij_x_q2ij->item(i,j) !=0)){
                          
                                      a2=tempS2ixmij_x_q2ij->item(i,j)->data(0).toDouble();
                                      coef2= coef2 + a2;
                                  }
                          
                              }
                              curItem=new QTableWidgetItem;
                              curItem->setData(0,coef);
                              table->setItem(3,c,curItem);
                          
                              curItem2=new QTableWidgetItem;
                              curItem2->setData(0,coef2);
                              table->setItem(3,c,curItem2);
                              c=c+1;
                          
                          }
                          

                          }
                          @

                          Let us assume that each iteration of your outer loop takes roughly 10 to 40ms. That is, after each iteration, we would like to return to the event loop. This is how you could do that:

                          @
                          //calculation, version 3
                          void FormdP0j_Poj::calculate()
                          {
                          //calcul des coefficients
                          m_working = true; // declared as bool class member
                          m_workCurrentIteration = 0; //declared as int class member
                          m_workIterationCount = tempS1ixmij_x_q1ij->columnCount(); //also an int member

                          QTimer::singleShot(0, this, SLOT(doWorkIteration()));
                          }

                          //declared as slot in the class declaration
                          void FormdP0j_poj::doWorkIteration()
                          {
                          // you seem to be missing some variable declarations. Did you cut those out?

                          int j = m_workCurrentIteration;
                          
                              c=1; coef=0.; //where are these declared?
                              for( int i=1 ; j < tempS1ixmij_x_q1ij->rowCount()  ;i=i+1 )
                              {
                                  if ((tempS1ixmij_x_q1ij->item(i,j) !=0)){
                          
                                      a=tempS1ixmij_x_q1ij->item(i,j)->data(0).toDouble();
                                      coef= coef + a;
                                  }
                          
                                  if ((tempS2ixmij_x_q2ij->item(i,j) !=0)){
                          
                                      a2=tempS2ixmij_x_q2ij->item(i,j)->data(0).toDouble();
                                      coef2= coef2 + a2;
                                  }
                          
                              }
                              curItem=new QTableWidgetItem;
                              curItem->setData(0,coef);
                              table->setItem(3,c,curItem);
                          
                              curItem2=new QTableWidgetItem;
                              curItem2->setData(0,coef2);
                              table->setItem(3,c,curItem);
                              c=c+1;
                          
                          }
                          

                          //prepare for the next iteration
                          ++m_workCurrentIteration;
                          if (m_workCurrentIteration < m_workIterationCount) {
                          //this is the trick: we schedule another iteration to be calculated if we need to do more work
                          QTimer::singleShot(0, this, SLOT(doWorkIteration()));
                          } else {
                          m_working = false;
                          workDone();
                          }
                          }

                          void FormdP0j_poj::workDone()
                          {
                          // this method is called when all the iterations are done. You might want to update the GUI to reflect that the calculation is done.
                          }
                          @

                          A method like this will make sure you return to your eventloop regulary, thus giving your GUI the chance to update. Note that it will not make it run faster. In fact, it will be slower. But it will keep your users more happy. Using a thread might make your code faster, as your code can potentially use more cores in a multi-core machine. However, if you want to use threads, you can not interweave creating QTableWidgetItems into the calculation code. Instead, you'd have to store the results elsewhere. If you want to go that route, I think using QtConcurrent would be a feasable way to go.

                          disclaimer: all code presented here has just been typed into the editor of the forum. It is not tested, and only intended as an example.

                          1 Reply Last reply
                          0
                          • Z Offline
                            Z Offline
                            ZapB
                            wrote on 26 Jun 2011, 11:49 last edited by
                            #17

                            The new operator is a very expensive operation to call in a loop. You may get a reasonable improvement by calculating how many QTableWidgetItem's you actually need and new'ing them all in one go. Then in you loop just set the properties of each item as you do now.

                            Using some sort of profiling tool such as valgrind (on Linux) will tell you where to focus your optimisation efforts.

                            Nokia Certified Qt Specialist
                            Interested in hearing about Qt related work

                            1 Reply Last reply
                            0
                            • M Offline
                              M Offline
                              maxoreli
                              wrote on 27 Jun 2011, 07:05 last edited by
                              #18

                              Now,I remove new's operator in my loop,however ,program is slower
                              [quote author="ZapB" date="1309088968"]The new operator is a very expensive operation to call in a loop. You may get a reasonable improvement by calculating how many QTableWidgetItem's you actually need and new'ing them all in one go. Then in you loop just set the properties of each item as you do now.

                              Using some sort of profiling tool such as valgrind (on Linux) will tell you where to focus your optimisation efforts.[/quote]

                              1 Reply Last reply
                              0
                              • A Offline
                                A Offline
                                andre
                                wrote on 27 Jun 2011, 07:11 last edited by
                                #19

                                [quote author="maxoreli" date="1309158340"] Now,I remove new's operator in my loop,however ,program is slower
                                [/quote]
                                Curious how you did that...

                                1 Reply Last reply
                                0
                                • M Offline
                                  M Offline
                                  maxoreli
                                  wrote on 27 Jun 2011, 07:44 last edited by
                                  #20

                                  that's my new method setupContents()
                                  @
                                  void FormdP0j_Poj::setupContents()
                                  {

                                  FormS0ixmij_x_q0ij *matrixS0ixmij_x_q0ij=new  FormS0ixmij_x_q0ij;
                                  
                                  FormS1ixmij_x_q1ij *matrixS1ixmij_x_q1ij=new FormS1ixmij_x_q1ij;
                                  
                                  FormS2ixmij_x_q2ij *matrixS2ixmij_x_q2ij=new FormS2ixmij_x_q2ij;
                                  
                                  
                                  tempS0ixmij_x_q0ij= matrixS0ixmij_x_q0ij->getTable();
                                  tempS1ixmij_x_q1ij= matrixS1ixmij_x_q1ij->getTable();
                                  tempS2ixmij_x_q2ij= matrixS2ixmij_x_q2ij->getTable();
                                  

                                  // QCoreApplication::processEvents();

                                  QVariant variant;
                                  //QTableWidgetItem * curItem=new QTableWidgetItem;
                                  progressDialog.setRange(0,tempS0ixmij_x_q0ij->columnCount() );
                                  progressDialog.setMinimumDuration(0);
                                  
                                  
                                  if( (tempS0ixmij_x_q0ij!=0)   &&  (tempS1ixmij_x_q1ij !=0) && (tempS2ixmij_x_q2ij !=0) )
                                  {
                                  
                                  
                                      //copie de l'entete
                                      int c=1;
                                      table->setItem(1,0,new QTableWidgetItem(QString("dP0j/P0j")));
                                      table->setItem(2,0,new QTableWidgetItem(QString("dP1j/P1j")));
                                      table->setItem(3,0,new QTableWidgetItem(QString("dP2j/P2j")));
                                  
                                      int nbCols=tempS0ixmij_x_q0ij->columnCount() ;
                                      
                                       //that's there!!
                                      QTableWidgetItem *cur=new QTableWidgetItem[nbCols];
                                  
                                      for(int j=1; j < nbCols ;j=j+1)
                                      {
                                          if( tempS0ixmij_x_q0ij->item(0,j)!=0)
                                          {
                                              //curItem=new QTableWidgetItem;
                                              variant= tempS0ixmij_x_q0ij->item(0,j)->data(0);
                                              cur[j].setData(0,variant);
                                              table->setItem(0,c,&cur[j]);
                                              c=c+1;
                                          }
                                  
                                          progressDialog.setValue(j);
                                          progressDialog.setLabelText(tr("Processing ...Please wait"));
                                  
                                      }
                                      progressDialog.setValue(nbCols);
                                  
                                  
                                      table->resizeColumnsToContents();
                                      table->resizeRowsToContents();
                                      horizontalLayout->addWidget(table);
                                  }
                                  

                                  }
                                  @

                                  Hello Andre ,how are you. I tried your codes,that's Ok.As you said,my program is always slower.
                                  Now,I decide to remove QTableWidgetItem,I will find a manner to store the results.So ,I want to use Qthreads,we suppose that QTableWidgetItem is not present in code.What will be Code.
                                  Thanks For Advance and excuse me for disturbance...

                                  1 Reply Last reply
                                  0
                                  • A Offline
                                    A Offline
                                    andre
                                    wrote on 27 Jun 2011, 07:57 last edited by
                                    #21

                                    Sorry, I am not going to write it all out for you again. You'll have to do some work yourself too.

                                    1 Reply Last reply
                                    0
                                    • M Offline
                                      M Offline
                                      maxoreli
                                      wrote on 27 Jun 2011, 08:07 last edited by
                                      #22

                                      Ok ,I'm trying something,and i reply you once time over.
                                      And about the preview code,is it good?
                                      [quote author="Andre" date="1309161441"]Sorry, I am not going to write it all out for you again. You'll have to do some work yourself too.
                                      [/quote]

                                      1 Reply Last reply
                                      0
                                      • A Offline
                                        A Offline
                                        andre
                                        wrote on 27 Jun 2011, 08:09 last edited by
                                        #23

                                        [quote author="maxoreli" date="1309162036"]Ok ,I'm trying something,and i reply you once time over.
                                        And about the preview code,is it good?
                                        [quote author="Andre" date="1309161441"]Sorry, I am not going to write it all out for you again. You'll have to do some work yourself too.
                                        [/quote]

                                        [/quote]
                                        It might be my limited understanding of the English language, but I have no clue what you are asking me here. Could you rephrase, please?

                                        1 Reply Last reply
                                        0
                                        • M Offline
                                          M Offline
                                          maxoreli
                                          wrote on 27 Jun 2011, 08:34 last edited by
                                          #24

                                          I ask you if the preview code on QTableWidgetItems is correct for best performance!!!

                                          [quote author="Andre" date="1309162192"]
                                          [quote author="maxoreli" date="1309162036"]Ok ,I'm trying something,and i reply you once time over.
                                          And about the preview code,is it good?
                                          [quote author="Andre" date="1309161441"]Sorry, I am not going to write it all out for you again. You'll have to do some work yourself too.
                                          [/quote]

                                          [/quote]
                                          It might be my limited understanding of the English language, but I have no clue what you are asking me here. Could you rephrase, please?

                                          [/quote]

                                          1 Reply Last reply
                                          0

                                          14/26

                                          26 Jun 2011, 06:48

                                          • Login

                                          • Login or register to search.
                                          14 out of 26
                                          • First post
                                            14/26
                                            Last post
                                          0
                                          • Categories
                                          • Recent
                                          • Tags
                                          • Popular
                                          • Users
                                          • Groups
                                          • Search
                                          • Get Qt Extensions
                                          • Unsolved