Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Either `QFileInfo` caching does not work, or just its methods are unreasonable (very) slow
Forum Updated to NodeBB v4.3 + New Features

Either `QFileInfo` caching does not work, or just its methods are unreasonable (very) slow

Scheduled Pinned Locked Moved Unsolved General and Desktop
19 Posts 4 Posters 2.5k 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.
  • R RTEDFD

    QFileInfo::stat() does what it should and I don't see why it should return some kind of a structure because the structure is the QFileInfo instance.

    Does QFileInfo contain dev, ino, mode, nlink, uid, gid, rdev, blksize, blocks?

    It looks that Qt just ignores that data (while it can return them), so if stat returns that data it would be useful.

    It works such way, for example:

    • In Node.js: https://nodejs.org/api/fs.html#fsstatpath-options-callback
    • In Python: https://docs.python.org/3/library/os.html#os.stat

    JonBJ Offline
    JonBJ Offline
    JonB
    wrote on last edited by
    #8

    @RTEDFD
    No QFileInfo does not have any of those. Qt calls like this are designed to be OS-independent, hence the behaviour of QFileInfo::stat(). If you want those you will need to do a Linux (or Windows) call.

    1 Reply Last reply
    1
    • R RTEDFD

      QFileInfo::stat() does what it should and I don't see why it should return some kind of a structure because the structure is the QFileInfo instance.

      Does QFileInfo contain dev, ino, mode, nlink, uid, gid, rdev, blksize, blocks?

      It looks that Qt just ignores that data (while it can return them), so if stat returns that data it would be useful.

      It works such way, for example:

      • In Node.js: https://nodejs.org/api/fs.html#fsstatpath-options-callback
      • In Python: https://docs.python.org/3/library/os.html#os.stat

      Christian EhrlicherC Offline
      Christian EhrlicherC Offline
      Christian Ehrlicher
      Lifetime Qt Champion
      wrote on last edited by
      #9

      @RTEDFD said in Either `QFileInfo` caching does not work, or just its methods are unreasonable (very) slow:

      uid, gid

      Yes - https://doc.qt.io/qt-5/qfileinfo.html#groupId and https://doc.qt.io/qt-5/qfileinfo.html#ownerId

      The rest is to OS-specific as @JonB aleady said.

      Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
      Visit the Qt Academy at https://academy.qt.io/catalog

      1 Reply Last reply
      1
      • Christian EhrlicherC Offline
        Christian EhrlicherC Offline
        Christian Ehrlicher
        Lifetime Qt Champion
        wrote on last edited by Christian Ehrlicher
        #10

        Ok, I think the caching works, it's the QDateTime creation. You can prove that when you add

          for (QFileInfo &fileInfo : fileInfoList) {
            fileInfo.setCaching(false);
          }
        

        After you gathered the file information.

        /edit:
        Looks like it's the QDateTime conversion from UTC to localTime here. This is done after the cache and therefore executed every time. Removing toLocalTime() gives very impressive results:

        with .toLocalTime()
        [timer][sort(QList<MyFileInfo>)]: 35 ms
        [timer][sort(QList<MyFileInfo>)]: 30 ms
        [timer][sort(QList<QFileInfo>)]: 176 ms
        [timer][sort(QList<QFileInfo>)]: 169 ms
        
        without .toLocalTime()
        [timer][sort(QList<MyFileInfo>)]: 3 ms
        [timer][sort(QList<MyFileInfo>)]: 2 ms
        [timer][sort(QList<QFileInfo>)]: 5 ms
        [timer][sort(QList<QFileInfo>)]: 3 ms
        

        Source code: https://code.woboq.org/qt5/qtbase/src/corelib/io/qfileinfo.cpp.html#_ZNK9QFileInfo8fileTimeEN11QFileDevice8FileTimeE

        QDateTime::toLocalTime() calls some OS tz - Functions and one of this is calling getenv() which is the bottleneck here on Linux. Think it's a similar thing on Windows.

        Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
        Visit the Qt Academy at https://academy.qt.io/catalog

        1 Reply Last reply
        2
        • R Offline
          R Offline
          RTEDFD
          wrote on last edited by RTEDFD
          #11

          Most likely it is.

          Since the caching code is pretty simple*: https://github.com/qt/qtbase/blob/f29566c5a41c127eacaf13f3dbfe4624e55bc83f/src/corelib/io/qfileinfo.cpp#L191-L218

          It checks does there a value in the array, if it does, returns it, so the performance should be the same as when I read it from MyFileInfo object.


          *Also it caches ONLY the requested time, so if I need all 4 time values (M, B, C, A) I need to ask OS 4 times, while most likely the OS call returns all 4 times once. It's not optimal in terms of performance.

          Using of that stats method is overkill, since it is slower that calls of 4 methods (lastModified, birthTime, metadataChangeTime, lastRead). Currently with that 30000 files directory stat takes 1100 ms, only lastModified — 95 ms, all 4 times — 360 ms.

          JonBJ Christian EhrlicherC 2 Replies Last reply
          0
          • R RTEDFD

            Most likely it is.

            Since the caching code is pretty simple*: https://github.com/qt/qtbase/blob/f29566c5a41c127eacaf13f3dbfe4624e55bc83f/src/corelib/io/qfileinfo.cpp#L191-L218

            It checks does there a value in the array, if it does, returns it, so the performance should be the same as when I read it from MyFileInfo object.


            *Also it caches ONLY the requested time, so if I need all 4 time values (M, B, C, A) I need to ask OS 4 times, while most likely the OS call returns all 4 times once. It's not optimal in terms of performance.

            Using of that stats method is overkill, since it is slower that calls of 4 methods (lastModified, birthTime, metadataChangeTime, lastRead). Currently with that 30000 files directory stat takes 1100 ms, only lastModified — 95 ms, all 4 times — 360 ms.

            JonBJ Offline
            JonBJ Offline
            JonB
            wrote on last edited by
            #12

            @RTEDFD
            I looked at the code that @Christian-Ehrlicher has been looking at. Unfortunately you cannot influence/replace the conversion to localtime each time you call one of the filetime functions, and it uses internal Qt calls you cannot access so it's not possible to write a drop in replacement.

            So unless you want to wait for a possible fix --- which I think would mean them changing quite some code they may not be prepared to do --- if this speed issue breaks you you are left with are you prepared to use your own structure like you show so that you can hold the converted times for the files?

            1 Reply Last reply
            0
            • R RTEDFD

              Most likely it is.

              Since the caching code is pretty simple*: https://github.com/qt/qtbase/blob/f29566c5a41c127eacaf13f3dbfe4624e55bc83f/src/corelib/io/qfileinfo.cpp#L191-L218

              It checks does there a value in the array, if it does, returns it, so the performance should be the same as when I read it from MyFileInfo object.


              *Also it caches ONLY the requested time, so if I need all 4 time values (M, B, C, A) I need to ask OS 4 times, while most likely the OS call returns all 4 times once. It's not optimal in terms of performance.

              Using of that stats method is overkill, since it is slower that calls of 4 methods (lastModified, birthTime, metadataChangeTime, lastRead). Currently with that 30000 files directory stat takes 1100 ms, only lastModified — 95 ms, all 4 times — 360 ms.

              Christian EhrlicherC Offline
              Christian EhrlicherC Offline
              Christian Ehrlicher
              Lifetime Qt Champion
              wrote on last edited by Christian Ehrlicher
              #13

              @RTEDFD said in Either &#x60;QFileInfo&#x60; caching does not work, or just its methods are unreasonable (very) slow:

              *Also it caches ONLY the requested time, so if I need all 4 time values (M, B, C, A) I need to ask OS 4 times, while most likely the OS call returns all 4 times once. It's not optimal in terms of performance.

              You should really look and understand the code before ranting about something. You're wrong: https://code.qt.io/cgit/qt/qtbase.git/tree/src/corelib/io/qfilesystemengine_unix.cpp#n377

              Most likely it is.

              Not only most likely - see my numbers.

              Here again numbers for 30k files. With QDateTime::toLocalTime() 1.3s, without 0.07s.

              Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
              Visit the Qt Academy at https://academy.qt.io/catalog

              1 Reply Last reply
              2
              • Christian EhrlicherC Offline
                Christian EhrlicherC Offline
                Christian Ehrlicher
                Lifetime Qt Champion
                wrote on last edited by
                #14

                Here the bug report: https://bugreports.qt.io/browse/QTBUG-100349

                Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                Visit the Qt Academy at https://academy.qt.io/catalog

                1 Reply Last reply
                2
                • R Offline
                  R Offline
                  RTEDFD
                  wrote on last edited by RTEDFD
                  #15

                  It looks you run the code from the bug report in the debug mode.

                  When I run your code in the debug mode:

                  getFileInfos: 62
                  #files: 30000
                  myFileInfoList 93
                  bencMyFileInfo 19
                  bencQFileInfo 2925
                  

                  The difference is 150 times.

                  But when I run it in the release mode:

                  getFileInfos: 64
                  #files: 30000
                  myFileInfoList 93
                  bencMyFileInfo 2
                  bencQFileInfo 2879
                  

                  MyFileInfo sorting is 1439 times faster.

                  Christian EhrlicherC 1 Reply Last reply
                  0
                  • R RTEDFD

                    It looks you run the code from the bug report in the debug mode.

                    When I run your code in the debug mode:

                    getFileInfos: 62
                    #files: 30000
                    myFileInfoList 93
                    bencMyFileInfo 19
                    bencQFileInfo 2925
                    

                    The difference is 150 times.

                    But when I run it in the release mode:

                    getFileInfos: 64
                    #files: 30000
                    myFileInfoList 93
                    bencMyFileInfo 2
                    bencQFileInfo 2879
                    

                    MyFileInfo sorting is 1439 times faster.

                    Christian EhrlicherC Offline
                    Christian EhrlicherC Offline
                    Christian Ehrlicher
                    Lifetime Qt Champion
                    wrote on last edited by
                    #16

                    @RTEDFD said in Either &#x60;QFileInfo&#x60; caching does not work, or just its methods are unreasonable (very) slow:

                    It looks you run the code from the bug report in the debug mode.

                    I don't see what it should matter - the problem was identified and it the testcase properly shows it.

                    Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                    Visit the Qt Academy at https://academy.qt.io/catalog

                    1 Reply Last reply
                    0
                    • Christian EhrlicherC Offline
                      Christian EhrlicherC Offline
                      Christian Ehrlicher
                      Lifetime Qt Champion
                      wrote on last edited by
                      #17

                      Quite old but in qt6.6 QDateTime::lastModified() gained a new parameter 'QTimeZone' where you can pass QTimeZone::UTC to avoid conversion to the local time.
                      See also https://codereview.qt-project.org/c/qt/qtbase/+/437009

                      Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                      Visit the Qt Academy at https://academy.qt.io/catalog

                      R 1 Reply Last reply
                      3
                      • Christian EhrlicherC Christian Ehrlicher

                        Quite old but in qt6.6 QDateTime::lastModified() gained a new parameter 'QTimeZone' where you can pass QTimeZone::UTC to avoid conversion to the local time.
                        See also https://codereview.qt-project.org/c/qt/qtbase/+/437009

                        R Offline
                        R Offline
                        RTEDFD
                        wrote on last edited by RTEDFD
                        #18

                        Only for QDateTime::lastModified()?

                        The problem exists with the other times too.

                        For example, birthTime() and metadataChangeTime() are affected with this issue too.

                        JonBJ 1 Reply Last reply
                        0
                        • R RTEDFD

                          Only for QDateTime::lastModified()?

                          The problem exists with the other times too.

                          For example, birthTime() and metadataChangeTime() are affected with this issue too.

                          JonBJ Offline
                          JonBJ Offline
                          JonB
                          wrote on last edited by
                          #19

                          @RTEDFD
                          https://bugreports.qt.io/browse/QTBUG-100349 states:

                          Should be fixed in Qt 6.6 https://codereview.qt-project.org/c/qt/qtbase/+/437009

                          You can now pass a QTimeZone to any of the QFileInfo file times related methods to specify which time zone returned times should be in

                          So should apply to e.g. birthTime() too, but awaits Qt6.6..

                          1 Reply Last reply
                          1
                          • JonBJ JonB referenced this topic on

                          • Login

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