Avoid wasting time or how to avoid initialization

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Alexander Malkis

    Avoid wasting time or how to avoid initialization

    A real-life example:

    int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
    //...do smth with p
    if(depth) {
    Move m;
    int val=alpha_beta( depth-1,p,m /*,other args*/);
    }
    //...
    //sometimes change m, e.g.:
    if(depth==globa l_depth) m=best_move;
    //...return...
    }

    The problem here is that the (perhaps, default) constructor for m is
    called. It may do as little as he wish, but nevertheless he inits all
    the members of Move. It's time-consuming. But we don't need initializing
    at all, since the "Move m" declaration is needed only to let the
    recursively called fucntion sometimes change m.

    In C, if M were a struct, no init were performed and we had no problem.
    But what to do in C++ without too much hack?

    --
    Best regards,
    Alex.

    PS. To email me, remove "loeschedie s" from the email address given.
  • John Harrison

    #2
    Re: Avoid wasting time or how to avoid initialization


    "Alexander Malkis" <alexloeschedie smalk@stone.cs. uni-sb.de> wrote in message
    news:c51d7t$153 h$1@hades.rz.un i-saarland.de...[color=blue]
    > A real-life example:
    >
    > int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
    > //...do smth with p
    > if(depth) {
    > Move m;
    > int val=alpha_beta( depth-1,p,m /*,other args*/);
    > }
    > //...
    > //sometimes change m, e.g.:
    > if(depth==globa l_depth) m=best_move;
    > //...return...
    > }
    >
    > The problem here is that the (perhaps, default) constructor for m is
    > called. It may do as little as he wish, but nevertheless he inits all
    > the members of Move. It's time-consuming. But we don't need initializing
    > at all, since the "Move m" declaration is needed only to let the
    > recursively called fucntion sometimes change m.
    >
    > In C, if M were a struct, no init were performed and we had no problem.
    > But what to do in C++ without too much hack?[/color]

    What's in Move?

    If Move is a POD type (the only type you are allowed in C) then
    initialisation will not happen in C++ either. Something like this

    struct Move
    {
    char from_square;
    char to_square;
    char captured_piece;
    char promoted_piece;
    };

    isn't going to get initialised in either C or C++.

    john


    Comment

    • John Harrison

      #3
      Re: Avoid wasting time or how to avoid initialization


      "Alexander Malkis" <alexloeschedie smalk@stone.cs. uni-sb.de> wrote in message
      news:c51d7t$153 h$1@hades.rz.un i-saarland.de...[color=blue]
      > A real-life example:
      >
      > int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
      > //...do smth with p
      > if(depth) {
      > Move m;
      > int val=alpha_beta( depth-1,p,m /*,other args*/);
      > }
      > //...
      > //sometimes change m, e.g.:
      > if(depth==globa l_depth) m=best_move;
      > //...return...
      > }
      >
      > The problem here is that the (perhaps, default) constructor for m is
      > called. It may do as little as he wish, but nevertheless he inits all
      > the members of Move. It's time-consuming. But we don't need initializing
      > at all, since the "Move m" declaration is needed only to let the
      > recursively called fucntion sometimes change m.
      >
      > In C, if M were a struct, no init were performed and we had no problem.
      > But what to do in C++ without too much hack?[/color]

      What's in Move?

      If Move is a POD type (the only type you are allowed in C) then
      initialisation will not happen in C++ either. Something like this

      struct Move
      {
      char from_square;
      char to_square;
      char captured_piece;
      char promoted_piece;
      };

      isn't going to get initialised in either C or C++.

      john


      Comment

      • Leor Zolman

        #4
        Re: Avoid wasting time or how to avoid initialization

        On Wed, 07 Apr 2004 19:19:26 +0200, Alexander Malkis
        <alexloeschedie smalk@stone.cs. uni-sb.de> wrote:
        [color=blue]
        >A real-life example:
        >
        >int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
        >//...do smth with p
        > if(depth) {
        > Move m;
        > int val=alpha_beta( depth-1,p,m /*,other args*/);
        > }
        >//...
        >//sometimes change m, e.g.:
        >if(depth==glob al_depth) m=best_move;
        >//...return...
        >}
        >
        >The problem here is that the (perhaps, default) constructor for m is
        >called. It may do as little as he wish, but nevertheless he inits all
        >the members of Move. It's time-consuming. But we don't need initializing
        >at all, since the "Move m" declaration is needed only to let the
        >recursively called fucntion sometimes change m.
        >
        >In C, if M were a struct, no init were performed and we had no problem.
        >But what to do in C++ without too much hack?[/color]

        If, in C, there were "no init" performed, you'd have garbage in the struct.

        What does Move look like? Is it a POD (plain old data) type? If so, and
        you don't care whether the POD data members get initialized or not
        (presumably there's something in the logic of your code that would know not
        to actually look into the object in that case, since you're saying that was
        the case in C), then the constructor, such as it is, would be "trivial" and
        optimized away to nothing.

        If, on the other hand, Move is not POD and there needs to be a constructor,
        then you're doing something differently than you did in C anyway, and you
        probably wouldn't /want/ the initialization skipped...
        -leor


        --
        Leor Zolman --- BD Software --- www.bdsoft.com
        On-Site Training in C/C++, Java, Perl and Unix
        C++ users: Download BD Software's free STL Error Message Decryptor at:
        An STL Error Decryptor for C++ by Leor Zolman of BD Software - available to download here

        Comment

        • Leor Zolman

          #5
          Re: Avoid wasting time or how to avoid initialization

          On Wed, 07 Apr 2004 19:19:26 +0200, Alexander Malkis
          <alexloeschedie smalk@stone.cs. uni-sb.de> wrote:
          [color=blue]
          >A real-life example:
          >
          >int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
          >//...do smth with p
          > if(depth) {
          > Move m;
          > int val=alpha_beta( depth-1,p,m /*,other args*/);
          > }
          >//...
          >//sometimes change m, e.g.:
          >if(depth==glob al_depth) m=best_move;
          >//...return...
          >}
          >
          >The problem here is that the (perhaps, default) constructor for m is
          >called. It may do as little as he wish, but nevertheless he inits all
          >the members of Move. It's time-consuming. But we don't need initializing
          >at all, since the "Move m" declaration is needed only to let the
          >recursively called fucntion sometimes change m.
          >
          >In C, if M were a struct, no init were performed and we had no problem.
          >But what to do in C++ without too much hack?[/color]

          If, in C, there were "no init" performed, you'd have garbage in the struct.

          What does Move look like? Is it a POD (plain old data) type? If so, and
          you don't care whether the POD data members get initialized or not
          (presumably there's something in the logic of your code that would know not
          to actually look into the object in that case, since you're saying that was
          the case in C), then the constructor, such as it is, would be "trivial" and
          optimized away to nothing.

          If, on the other hand, Move is not POD and there needs to be a constructor,
          then you're doing something differently than you did in C anyway, and you
          probably wouldn't /want/ the initialization skipped...
          -leor


          --
          Leor Zolman --- BD Software --- www.bdsoft.com
          On-Site Training in C/C++, Java, Perl and Unix
          C++ users: Download BD Software's free STL Error Message Decryptor at:
          An STL Error Decryptor for C++ by Leor Zolman of BD Software - available to download here

          Comment

          • bartek

            #6
            Re: Avoid wasting time or how to avoid initialization

            Alexander Malkis <alexloeschedie smalk@stone.cs. uni-sb.de> wrote in
            news:c51d7t$153 h$1@hades.rz.un i-saarland.de:
            [color=blue]
            > A real-life example:
            >
            > int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
            > //...do smth with p
            > if(depth) {
            > Move m;
            > int val=alpha_beta( depth-1,p,m /*,other args*/);
            > }
            > //...
            > //sometimes change m, e.g.:
            > if(depth==globa l_depth) m=best_move;
            > //...return...
            > }
            >
            > The problem here is that the (perhaps, default) constructor for m is
            > called. It may do as little as he wish, but nevertheless he inits all
            > the members of Move. It's time-consuming. But we don't need[/color]
            initializing[color=blue]
            > at all, since the "Move m" declaration is needed only to let the
            > recursively called fucntion sometimes change m.
            >
            > In C, if M were a struct, no init were performed and we had no problem.
            > But what to do in C++ without too much hack?
            >[/color]

            I don't quite understand the rationale... Is the 'Move& m' meant as an
            output argument?

            Anyway... why don't you use a pointer to Move then? (or better ... a
            smart pointer?) You could then construct an instance at the point it's a
            ctually needed.

            Cheers!

            Comment

            • bartek

              #7
              Re: Avoid wasting time or how to avoid initialization

              Alexander Malkis <alexloeschedie smalk@stone.cs. uni-sb.de> wrote in
              news:c51d7t$153 h$1@hades.rz.un i-saarland.de:
              [color=blue]
              > A real-life example:
              >
              > int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
              > //...do smth with p
              > if(depth) {
              > Move m;
              > int val=alpha_beta( depth-1,p,m /*,other args*/);
              > }
              > //...
              > //sometimes change m, e.g.:
              > if(depth==globa l_depth) m=best_move;
              > //...return...
              > }
              >
              > The problem here is that the (perhaps, default) constructor for m is
              > called. It may do as little as he wish, but nevertheless he inits all
              > the members of Move. It's time-consuming. But we don't need[/color]
              initializing[color=blue]
              > at all, since the "Move m" declaration is needed only to let the
              > recursively called fucntion sometimes change m.
              >
              > In C, if M were a struct, no init were performed and we had no problem.
              > But what to do in C++ without too much hack?
              >[/color]

              I don't quite understand the rationale... Is the 'Move& m' meant as an
              output argument?

              Anyway... why don't you use a pointer to Move then? (or better ... a
              smart pointer?) You could then construct an instance at the point it's a
              ctually needed.

              Cheers!

              Comment

              • Alexander Malkis

                #8
                Re: Avoid wasting time or how to avoid initialization

                //Here is the Move. It's not chess,
                //but an edge-moving game which is a bit complex here to explain.
                //Edge is also a class.

                class Move {
                public:
                Edge from, to; //where do we take an edge and where do we place it
                //constructor
                Move(Edge from_e, Edge to_e): from(from_e), to(to_e) { }
                //default-constructor
                Move() { }
                class ErrorBadInput { }; //the caller has to eat the input itself
                friend std::ostream& operator<<(std: :ostream&, const Move&); //output
                friend std::istream& operator>>(std: :istream&, Move&); //input
                };

                /* So as far as I understood, changing it to struct would suffice. The
                problem is that the other (nondefault) constructor should be removed
                also. It works but is not quite what I want, since the class is going to
                grow and will sooner or later need some more member functions.

                In my example, I really want to avoid initialization in this case and
                "garbage" in m is ok:
                */
                //...
                if(depth) {
                Move m;
                int val=alpha_beta( depth-1,p,m /*,other args*/);
                }
                //...
                /* The idea of a pointer gets quite messy, since the Move object would
                be destroyed not in the call of alpha_beta that has created it, in
                general not in alpha_beta at all. And the additional logic has to be
                implemented to tell when to delete an m and when not, which has nothing
                to do with algorithm itself.
                */
                int alpha_beta(..., Move* &m) {
                ....
                Move *m;
                int val=alpha_beta( depth-1,p,m /*,other args*/);
                if(m)...
                else ...
                ....
                if(...) m=new Move(...); else m=NULL;
                }
                /*
                The smart pointer implies (as far I understand these) an time-overhead.
                */

                --
                Best regards,
                Alex.

                PS. To email me, remove "loeschedie s" from the email address given.

                Comment

                • Alexander Malkis

                  #9
                  Re: Avoid wasting time or how to avoid initialization

                  //Here is the Move. It's not chess,
                  //but an edge-moving game which is a bit complex here to explain.
                  //Edge is also a class.

                  class Move {
                  public:
                  Edge from, to; //where do we take an edge and where do we place it
                  //constructor
                  Move(Edge from_e, Edge to_e): from(from_e), to(to_e) { }
                  //default-constructor
                  Move() { }
                  class ErrorBadInput { }; //the caller has to eat the input itself
                  friend std::ostream& operator<<(std: :ostream&, const Move&); //output
                  friend std::istream& operator>>(std: :istream&, Move&); //input
                  };

                  /* So as far as I understood, changing it to struct would suffice. The
                  problem is that the other (nondefault) constructor should be removed
                  also. It works but is not quite what I want, since the class is going to
                  grow and will sooner or later need some more member functions.

                  In my example, I really want to avoid initialization in this case and
                  "garbage" in m is ok:
                  */
                  //...
                  if(depth) {
                  Move m;
                  int val=alpha_beta( depth-1,p,m /*,other args*/);
                  }
                  //...
                  /* The idea of a pointer gets quite messy, since the Move object would
                  be destroyed not in the call of alpha_beta that has created it, in
                  general not in alpha_beta at all. And the additional logic has to be
                  implemented to tell when to delete an m and when not, which has nothing
                  to do with algorithm itself.
                  */
                  int alpha_beta(..., Move* &m) {
                  ....
                  Move *m;
                  int val=alpha_beta( depth-1,p,m /*,other args*/);
                  if(m)...
                  else ...
                  ....
                  if(...) m=new Move(...); else m=NULL;
                  }
                  /*
                  The smart pointer implies (as far I understand these) an time-overhead.
                  */

                  --
                  Best regards,
                  Alex.

                  PS. To email me, remove "loeschedie s" from the email address given.

                  Comment

                  • John Harrison

                    #10
                    Re: Avoid wasting time or how to avoid initialization


                    "Alexander Malkis" <alexloeschedie smalk@stone.cs. uni-sb.de> wrote in message
                    news:c51kc8$17n f$1@hades.rz.un i-saarland.de...[color=blue]
                    > //Here is the Move. It's not chess,
                    > //but an edge-moving game which is a bit complex here to explain.
                    > //Edge is also a class.
                    >
                    > class Move {
                    > public:
                    > Edge from, to; //where do we take an edge and where do we place it
                    > //constructor
                    > Move(Edge from_e, Edge to_e): from(from_e), to(to_e) { }
                    > //default-constructor
                    > Move() { }
                    > class ErrorBadInput { }; //the caller has to eat the input itself
                    > friend std::ostream& operator<<(std: :ostream&, const Move&); //output
                    > friend std::istream& operator>>(std: :istream&, Move&); //input
                    > };
                    >
                    > /* So as far as I understood, changing it to struct would suffice. The
                    > problem is that the other (nondefault) constructor should be removed
                    > also. It works but is not quite what I want, since the class is going to
                    > grow and will sooner or later need some more member functions.
                    >[/color]

                    Struct make no difference at all.

                    Give Edge a similar constructor to Move and I would expect a compiler to be
                    smart enough to optimise away both constructor calls.

                    john


                    Comment

                    • John Harrison

                      #11
                      Re: Avoid wasting time or how to avoid initialization


                      "Alexander Malkis" <alexloeschedie smalk@stone.cs. uni-sb.de> wrote in message
                      news:c51kc8$17n f$1@hades.rz.un i-saarland.de...[color=blue]
                      > //Here is the Move. It's not chess,
                      > //but an edge-moving game which is a bit complex here to explain.
                      > //Edge is also a class.
                      >
                      > class Move {
                      > public:
                      > Edge from, to; //where do we take an edge and where do we place it
                      > //constructor
                      > Move(Edge from_e, Edge to_e): from(from_e), to(to_e) { }
                      > //default-constructor
                      > Move() { }
                      > class ErrorBadInput { }; //the caller has to eat the input itself
                      > friend std::ostream& operator<<(std: :ostream&, const Move&); //output
                      > friend std::istream& operator>>(std: :istream&, Move&); //input
                      > };
                      >
                      > /* So as far as I understood, changing it to struct would suffice. The
                      > problem is that the other (nondefault) constructor should be removed
                      > also. It works but is not quite what I want, since the class is going to
                      > grow and will sooner or later need some more member functions.
                      >[/color]

                      Struct make no difference at all.

                      Give Edge a similar constructor to Move and I would expect a compiler to be
                      smart enough to optimise away both constructor calls.

                      john


                      Comment

                      • tom_usenet

                        #12
                        Re: Avoid wasting time or how to avoid initialization

                        On Wed, 07 Apr 2004 19:19:26 +0200, Alexander Malkis
                        <alexloeschedie smalk@stone.cs. uni-sb.de> wrote:
                        [color=blue]
                        >A real-life example:
                        >
                        >int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
                        >//...do smth with p
                        > if(depth) {
                        > Move m;
                        > int val=alpha_beta( depth-1,p,m /*,other args*/);
                        > }[/color]

                        I assume you can't just do:

                        if(depth) {
                        int val=alpha_beta( depth-1,p,m /*,other args*/);
                        }

                        i.e. just pass on the move from the level above? That would solve the
                        problem...

                        Tom
                        --
                        C++ FAQ: http://www.parashift.com/c++-faq-lite/
                        C FAQ: http://www.eskimo.com/~scs/C-faq/top.html

                        Comment

                        • tom_usenet

                          #13
                          Re: Avoid wasting time or how to avoid initialization

                          On Wed, 07 Apr 2004 19:19:26 +0200, Alexander Malkis
                          <alexloeschedie smalk@stone.cs. uni-sb.de> wrote:
                          [color=blue]
                          >A real-life example:
                          >
                          >int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
                          >//...do smth with p
                          > if(depth) {
                          > Move m;
                          > int val=alpha_beta( depth-1,p,m /*,other args*/);
                          > }[/color]

                          I assume you can't just do:

                          if(depth) {
                          int val=alpha_beta( depth-1,p,m /*,other args*/);
                          }

                          i.e. just pass on the move from the level above? That would solve the
                          problem...

                          Tom
                          --
                          C++ FAQ: http://www.parashift.com/c++-faq-lite/
                          C FAQ: http://www.eskimo.com/~scs/C-faq/top.html

                          Comment

                          • Howard

                            #14
                            Re: Avoid wasting time or how to avoid initialization

                            [color=blue][color=green]
                            > >
                            > >int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
                            > >//...do smth with p
                            > > if(depth) {
                            > > Move m;
                            > > int val=alpha_beta( depth-1,p,m /*,other args*/);
                            > > }[/color]
                            >
                            > I assume you can't just do:
                            >
                            > if(depth) {
                            > int val=alpha_beta( depth-1,p,m /*,other args*/);
                            > }
                            >
                            > i.e. just pass on the move from the level above? That would solve the
                            > problem...
                            >[/color]

                            That's what I thought you'd want, too. I'm confused by your declaring a
                            local m when one of the parameters is also named m. That's an indicator of
                            something wrong, usually.

                            -Howard




                            Comment

                            • Howard

                              #15
                              Re: Avoid wasting time or how to avoid initialization

                              [color=blue][color=green]
                              > >
                              > >int alpha_beta(unsi gned depth,Position p, Move& m /*,other args*/) {
                              > >//...do smth with p
                              > > if(depth) {
                              > > Move m;
                              > > int val=alpha_beta( depth-1,p,m /*,other args*/);
                              > > }[/color]
                              >
                              > I assume you can't just do:
                              >
                              > if(depth) {
                              > int val=alpha_beta( depth-1,p,m /*,other args*/);
                              > }
                              >
                              > i.e. just pass on the move from the level above? That would solve the
                              > problem...
                              >[/color]

                              That's what I thought you'd want, too. I'm confused by your declaring a
                              local m when one of the parameters is also named m. That's an indicator of
                              something wrong, usually.

                              -Howard




                              Comment

                              Working...