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. Can't reset QFlag in simple class
Forum Updated to NodeBB v4.3 + New Features

Can't reset QFlag in simple class

Scheduled Pinned Locked Moved Solved General and Desktop
16 Posts 4 Posters 1.8k Views 2 Watching
  • 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 mrjj
    4 Apr 2020, 12:24

    @Please_Help_me_D
    Hi
    yes a bool would act as a toggle but QFlags is
    actually more like a list of bools.
    You can then set one or more of these bools.

    so say you had something to describe a person

     enum MyFlag {
            Clever, // default
            Handsome,
           Rich
        };
    

    then
    flag.setFlag( Clever );
    flag.setFlag( Handsome );

    Then you set the flags for the person to be Clever and handsome.

    For your exmaple to make it flip/flop you would have to do
    flag.setFlag(Yes ,true ); // turn on
    flag.setFlag(Yes, false); // turn off
    flag.setFlag(No); // turn ON

    Setting No alone , will not turn off Yes.
    It means that No is on also. (or off)

    Hope this makes better sense then :)

    P Offline
    P Offline
    Please_Help_me_D
    wrote on 4 Apr 2020, 13:10 last edited by Please_Help_me_D 4 Apr 2020, 13:10
    #6

    @mrjj thank, now I understood but the problem is in this way they also don't work.
    I just tried to rewrite MyClass here it is:

    #include <QFlags>
    
    class MyClass
    {
    public:
        enum MyFlag {
            Yes, // default
            No
        };
        Q_DECLARE_FLAGS(MyFlags, MyFlag)
    
        MyClass(){
            flag.setFlag(Yes, true);
            bool a = flag.testFlag(Yes); // a == true
    
            flag.setFlag(Yes, false);
            bool b = flag.testFlag(Yes); // b == true
    
            flag.setFlag(Yes, true);
            bool c = flag.testFlag(Yes); // c == true
        }
    
    private:
        MyFlags flag;
    };
    

    Why all the three bool vars are true? Is that ok?
    6cc5c7b0-2e62-4e1f-9593-5cd74e6329c1-image.png

    1 Reply Last reply
    0
    • M Offline
      M Offline
      mrjj
      Lifetime Qt Champion
      wrote on 4 Apr 2020, 13:21 last edited by
      #7

      Hi
      I think its due to using a value of zero for one of the enums.

      try with

      enum MyFlag {
              Yes = 1, // default
              No =2
          };
      

      then it looks as expected
      alt text

      P 1 Reply Last reply 4 Apr 2020, 13:38
      2
      • M mrjj
        4 Apr 2020, 13:21

        Hi
        I think its due to using a value of zero for one of the enums.

        try with

        enum MyFlag {
                Yes = 1, // default
                No =2
            };
        

        then it looks as expected
        alt text

        P Offline
        P Offline
        Please_Help_me_D
        wrote on 4 Apr 2020, 13:38 last edited by
        #8

        @mrjj huh now it works :)
        thank you!

        1 Reply Last reply
        0
        • S Offline
          S Offline
          SGaist
          Lifetime Qt Champion
          wrote on 4 Apr 2020, 14:34 last edited by
          #9

          Hi,

          It is shown in and explained in the QFlags that each item of your flags need to have a different value (1 -> 2 -> 4 -> 8 -> etc.) that can be ORed otherwise you cannot establish which was set. You can do that using a binary format for your number, it will make things clearer.

          Interested in AI ? www.idiap.ch
          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

          P 1 Reply Last reply 4 Apr 2020, 21:17
          3
          • S SGaist
            4 Apr 2020, 14:34

            Hi,

            It is shown in and explained in the QFlags that each item of your flags need to have a different value (1 -> 2 -> 4 -> 8 -> etc.) that can be ORed otherwise you cannot establish which was set. You can do that using a binary format for your number, it will make things clearer.

            P Offline
            P Offline
            Please_Help_me_D
            wrote on 4 Apr 2020, 21:17 last edited by
            #10

            @SGaist thank you!
            But it is always difficult for me to read documentation about something new that I don't have any idea. It becomes much easier when I already have some representation about studied topic.
            As example I've read both this and that but nothing helped me to solve my task. I'm like a slowpoke :)
            But now when I know that QFlag is something like a list of boolean variables I can match documentation with my needs. I always search "how to solve my problem" in Internet and only then I disturb people from communities.
            This is just my excuses so you would not think that I don't do anything to solve my problem by myself :)

            I really appreciate forum's people help because you save a lot of time and nerves and honestly saying I would have never learned programming (Matlab and C/C++) if there were not such communities.

            M 1 Reply Last reply 4 Apr 2020, 21:57
            0
            • P Please_Help_me_D
              4 Apr 2020, 21:17

              @SGaist thank you!
              But it is always difficult for me to read documentation about something new that I don't have any idea. It becomes much easier when I already have some representation about studied topic.
              As example I've read both this and that but nothing helped me to solve my task. I'm like a slowpoke :)
              But now when I know that QFlag is something like a list of boolean variables I can match documentation with my needs. I always search "how to solve my problem" in Internet and only then I disturb people from communities.
              This is just my excuses so you would not think that I don't do anything to solve my problem by myself :)

              I really appreciate forum's people help because you save a lot of time and nerves and honestly saying I would have never learned programming (Matlab and C/C++) if there were not such communities.

              M Offline
              M Offline
              mrjj
              Lifetime Qt Champion
              wrote on 4 Apr 2020, 21:57 last edited by
              #11

              @Please_Help_me_D

              Hi
              Yes its like a list
              but to make it take up far less space, it uses bits instead of a bool.
              So basically QFlags helps you get/and set the bits.

              You know for programming a value can also be shown as binary 0 and 1 ?

              When you OR something, then just one of the bit has to be set then it becomes set in the result too.

              0 1 0 1 OR
              0 1 1 0
              -------
              0 1 1 1
              

              with AND operator both bits must be set to be set in the result.

              Thats how QFlags works interinally

              if we look at

               Q_DECL_RELAXED_CONSTEXPR inline QFlags &setFlag(Enum flag, bool on = true) noexcept
                  {
                      return on ? (*this |= flag) : (*this &= ~Int(flag));
                  }
              
              

              then it says

              if (on is true )
              value = value OR flag ( in your case yes )
              else if on is false ( to turn off )
              value = value AND (negative) flag

              the last part is taking out the bits that belong to the value for the flag.

              So AND / OR is not that difficult to understand at a high level as it simply
              manipulate the values as bits.

              P 1 Reply Last reply 4 Apr 2020, 22:44
              2
              • M mrjj
                4 Apr 2020, 21:57

                @Please_Help_me_D

                Hi
                Yes its like a list
                but to make it take up far less space, it uses bits instead of a bool.
                So basically QFlags helps you get/and set the bits.

                You know for programming a value can also be shown as binary 0 and 1 ?

                When you OR something, then just one of the bit has to be set then it becomes set in the result too.

                0 1 0 1 OR
                0 1 1 0
                -------
                0 1 1 1
                

                with AND operator both bits must be set to be set in the result.

                Thats how QFlags works interinally

                if we look at

                 Q_DECL_RELAXED_CONSTEXPR inline QFlags &setFlag(Enum flag, bool on = true) noexcept
                    {
                        return on ? (*this |= flag) : (*this &= ~Int(flag));
                    }
                
                

                then it says

                if (on is true )
                value = value OR flag ( in your case yes )
                else if on is false ( to turn off )
                value = value AND (negative) flag

                the last part is taking out the bits that belong to the value for the flag.

                So AND / OR is not that difficult to understand at a high level as it simply
                manipulate the values as bits.

                P Offline
                P Offline
                Please_Help_me_D
                wrote on 4 Apr 2020, 22:44 last edited by Please_Help_me_D 4 Apr 2020, 22:51
                #12

                @mrjj thank you!
                I understood something but some interesting things I don't. Here what I get.
                Yes I understand byte/bit

                This:

                on ? (*this |= flag) : (*this &= ~Int(flag));
                

                is equal to:

                if ( on == true ){
                    *this = (*this || flag);
                } else {
                    *this = (*this &~ Int(flag));
                }
                

                right?
                If so then to understand the mathematics I need to understand what in bit representation is: *this, flag, Int(flag)
                In my case flag is equal to 1 right ( enum MyFlag { Yes = 1} )? in bit representation 0001
                But what is in *this before assigning anything (operator =) and what function Int() does? simply converts flag to integer? as I know this type of casting doesn't change bits of the number it simply tells "these bits should be read as int"
                Something like that:)

                ||________________
                By the way how to turn on notifications when somebody answers me or writes in topic created by me?

                M 1 Reply Last reply 4 Apr 2020, 22:57
                0
                • P Please_Help_me_D
                  4 Apr 2020, 22:44

                  @mrjj thank you!
                  I understood something but some interesting things I don't. Here what I get.
                  Yes I understand byte/bit

                  This:

                  on ? (*this |= flag) : (*this &= ~Int(flag));
                  

                  is equal to:

                  if ( on == true ){
                      *this = (*this || flag);
                  } else {
                      *this = (*this &~ Int(flag));
                  }
                  

                  right?
                  If so then to understand the mathematics I need to understand what in bit representation is: *this, flag, Int(flag)
                  In my case flag is equal to 1 right ( enum MyFlag { Yes = 1} )? in bit representation 0001
                  But what is in *this before assigning anything (operator =) and what function Int() does? simply converts flag to integer? as I know this type of casting doesn't change bits of the number it simply tells "these bits should be read as int"
                  Something like that:)

                  ||________________
                  By the way how to turn on notifications when somebody answers me or writes in topic created by me?

                  M Offline
                  M Offline
                  mrjj
                  Lifetime Qt Champion
                  wrote on 4 Apr 2020, 22:57 last edited by mrjj 4 Apr 2020, 22:58
                  #13

                  @Please_Help_me_D

                  Yes odd syntax is called Conditional ternary operator:
                  but is just a one liner if else.

                  (condition) ? (if_true) : (if_false)

                  The *this de reference the this pointer.
                  so its what it points to.
                  This is done to trigger the operator = which QFlags have overloaded.
                  so its a way to assign the value to it self using =

                  the Int() is a type cast like (Int)flag;
                  But its a bit more if we look at source

                  #if defined(Q_CC_MSVC) || defined(Q_CLANG_QDOC)
                      // see above for MSVC
                      // the definition below is too complex for qdoc
                      typedef int Int;
                  #else
                      typedef typename std::conditional<
                              std::is_unsigned<typename std::underlying_type<Enum>::type>::value,
                              unsigned int,
                              signed int
                          >::type Int;
                  #endif
                  

                  so when not MSVC compiler it also checks the type

                  And if you think that looks strange, you are right :)

                  Its c++ templates and while really useful, its also
                  often ugly and unreadable. So ignore it until later in your training.

                  P 1 Reply Last reply 4 Apr 2020, 23:39
                  1
                  • M mrjj
                    4 Apr 2020, 22:57

                    @Please_Help_me_D

                    Yes odd syntax is called Conditional ternary operator:
                    but is just a one liner if else.

                    (condition) ? (if_true) : (if_false)

                    The *this de reference the this pointer.
                    so its what it points to.
                    This is done to trigger the operator = which QFlags have overloaded.
                    so its a way to assign the value to it self using =

                    the Int() is a type cast like (Int)flag;
                    But its a bit more if we look at source

                    #if defined(Q_CC_MSVC) || defined(Q_CLANG_QDOC)
                        // see above for MSVC
                        // the definition below is too complex for qdoc
                        typedef int Int;
                    #else
                        typedef typename std::conditional<
                                std::is_unsigned<typename std::underlying_type<Enum>::type>::value,
                                unsigned int,
                                signed int
                            >::type Int;
                    #endif
                    

                    so when not MSVC compiler it also checks the type

                    And if you think that looks strange, you are right :)

                    Its c++ templates and while really useful, its also
                    often ugly and unreadable. So ignore it until later in your training.

                    P Offline
                    P Offline
                    Please_Help_me_D
                    wrote on 4 Apr 2020, 23:39 last edited by Please_Help_me_D 4 Apr 2020, 23:42
                    #14

                    @mrjj all the things that depend on the compiler features are far outside of my current possibilities :)
                    So I think I begin to understand the magic behind QFlag.
                    returned value is of type bool and bool is not a single bit but rather a byte (maybe few bytes). So any numbers written in Yes except zero in this expression:

                    *this || flag
                    

                    returnes some byte (bytes) where even a single (or more) bits is not zero. A bool which has even a single (or more) non zero bit should return true right?
                    And I believe that behind this dark veil:

                    *this &~ Int(flag)
                    

                    are hidden all zeroed bits :)

                    By the way is it necessary to assign numbers to enum definitions (Yes, No etc) that are equal the power of 2 (1, 2, 4, 8, 16 ...)? as in many examples

                    M 1 Reply Last reply 5 Apr 2020, 06:41
                    0
                    • P Please_Help_me_D
                      4 Apr 2020, 23:39

                      @mrjj all the things that depend on the compiler features are far outside of my current possibilities :)
                      So I think I begin to understand the magic behind QFlag.
                      returned value is of type bool and bool is not a single bit but rather a byte (maybe few bytes). So any numbers written in Yes except zero in this expression:

                      *this || flag
                      

                      returnes some byte (bytes) where even a single (or more) bits is not zero. A bool which has even a single (or more) non zero bit should return true right?
                      And I believe that behind this dark veil:

                      *this &~ Int(flag)
                      

                      are hidden all zeroed bits :)

                      By the way is it necessary to assign numbers to enum definitions (Yes, No etc) that are equal the power of 2 (1, 2, 4, 8, 16 ...)? as in many examples

                      M Offline
                      M Offline
                      mrjj
                      Lifetime Qt Champion
                      wrote on 5 Apr 2020, 06:41 last edited by
                      #15

                      @Please_Help_me_D

                      Ok that's good :)
                      maybe you are ready for
                      https://www.youtube.com/watch?v=TKEaakjKrMc
                      Bitwise AND / OR

                      Actually the dark veil:
                      is using AND and BINARY NOT
                      to remove the bits for a flag

                      Yes, you must use power of 2 values as else some of the values will have
                      overlapping bit representation and things get funny when you combine certain flags.

                      P 1 Reply Last reply 5 Apr 2020, 12:09
                      1
                      • M mrjj
                        5 Apr 2020, 06:41

                        @Please_Help_me_D

                        Ok that's good :)
                        maybe you are ready for
                        https://www.youtube.com/watch?v=TKEaakjKrMc
                        Bitwise AND / OR

                        Actually the dark veil:
                        is using AND and BINARY NOT
                        to remove the bits for a flag

                        Yes, you must use power of 2 values as else some of the values will have
                        overlapping bit representation and things get funny when you combine certain flags.

                        P Offline
                        P Offline
                        Please_Help_me_D
                        wrote on 5 Apr 2020, 12:09 last edited by
                        #16

                        @mrjj thank you
                        Video helped me to remember what XOR. Also now it I understand how to easilly transform binary data representation to decimals :)

                        1 Reply Last reply
                        1

                        15/16

                        5 Apr 2020, 06:41

                        • Login

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