Help needed to build an array

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

    Help needed to build an array

    Hi

    I have a table with something like

    ID PARENT

    0 | -1
    1 | -1
    2 | 1
    3 | 1
    4 | 2
    5 | -1
    6 | 4

    And i want to build an array so i can output the data in the form

    0
    1
    |--2
    |----4
    | |----5
    |--3
    5

    Where 2 is a child of 1, and 4 is a child of 2 and so on.
    I could create an array like $data[$id][$parent] but how would i output the
    data where i get all the children of, say, ID=1 and all the children of ID =
    4.
    What would be the best way to achieve the above using MySQL db and php?

    If i read all the data sorted by PARENT i might be able to read the whole
    table at once and add all the data to one array?

    Any ideas?

    Regards.
    Simon/


  • John Smith

    #2
    Re: Help needed to build an array

    Children and Parents aren't used in Arrays, are you using Objects or
    Arrays???

    "Sims" <siminfrance@ho tmail.com> schreef in bericht
    news:c1vnh8$1ne iht$1@ID-162430.news.uni-berlin.de...[color=blue]
    > Hi
    >
    > I have a table with something like
    >
    > ID PARENT
    >
    > 0 | -1
    > 1 | -1
    > 2 | 1
    > 3 | 1
    > 4 | 2
    > 5 | -1
    > 6 | 4
    >
    > And i want to build an array so i can output the data in the form
    >
    > 0
    > 1
    > |--2
    > |----4
    > | |----5
    > |--3
    > 5
    >
    > Where 2 is a child of 1, and 4 is a child of 2 and so on.
    > I could create an array like $data[$id][$parent] but how would i output[/color]
    the[color=blue]
    > data where i get all the children of, say, ID=1 and all the children of ID[/color]
    =[color=blue]
    > 4.
    > What would be the best way to achieve the above using MySQL db and php?
    >
    > If i read all the data sorted by PARENT i might be able to read the whole
    > table at once and add all the data to one array?
    >
    > Any ideas?
    >
    > Regards.
    > Simon/
    >
    >[/color]


    Comment

    • Sims

      #3
      Re: Help needed to build an array

      Hi,

      "John Smith" <someone@nobody .com> wrote in message
      news:c1vq20$ro9 $1@news3.tilbu1 .nb.home.nl...[color=blue]
      > Children and Parents aren't used in Arrays, are you using Objects or
      > Arrays???
      >[/color]

      I am not using anything yet, i just want to know what would be the best way
      to read the data
      so that i can get the children(s) of all ids.

      It could be a class i guess, I want a function that would read the data from
      the database and build all the parents recursively so that i could, for
      example, get all the children for ID = 1 and i would return 2, 3.

      I want to build the array/class in one call of the database and not all
      every time i need to find the child of an ID.
      [color=blue][color=green]
      > > ID PARENT
      > >
      > > 0 | -1
      > > 1 | -1
      > > 2 | 1
      > > 3 | 1
      > > 4 | 2
      > > 5 | -1
      > > 6 | 4
      > >
      > > And i want to build an array so i can output the data in the form
      > >
      > > 0
      > > 1
      > > |--2
      > > |----4
      > > | |----5
      > > |--3
      > > 5
      > >
      > > Where 2 is a child of 1, and 4 is a child of 2 and so on.
      > > I could create an array like $data[$id][$parent] but how would i output[/color]
      > the[color=green]
      > > data where i get all the children of, say, ID=1 and all the children of[/color][/color]
      ID[color=blue]
      > =[color=green]
      > > 4.
      > > What would be the best way to achieve the above using MySQL db and php?
      > >
      > > If i read all the data sorted by PARENT i might be able to read the[/color][/color]
      whole[color=blue][color=green]
      > > table at once and add all the data to one array?
      > >
      > > Any ideas?
      > >
      > > Regards.
      > > Simon/
      > >
      > >[/color]
      >
      >[/color]


      Comment

      • col

        #4
        Re: Help needed to build an array


        "John Smith" <someone@nobody .com> wrote in message
        news:c1vq20$ro9 $1@news3.tilbu1 .nb.home.nl...[color=blue]
        > Children and Parents aren't used in Arrays, are you using Objects or
        > Arrays???
        >
        > "Sims" <siminfrance@ho tmail.com> schreef in bericht
        > news:c1vnh8$1ne iht$1@ID-162430.news.uni-berlin.de...[color=green]
        > > Hi
        > >
        > > I have a table with something like
        > >
        > > ID PARENT
        > >
        > > 0 | -1
        > > 1 | -1
        > > 2 | 1
        > > 3 | 1
        > > 4 | 2
        > > 5 | -1
        > > 6 | 4
        > >
        > > And i want to build an array so i can output the data in the form
        > >
        > > 0
        > > 1
        > > |--2
        > > |----4
        > > | |----5
        > > |--3
        > > 5
        > >
        > > Where 2 is a child of 1, and 4 is a child of 2 and so on.
        > > I could create an array like $data[$id][$parent] but how would i output[/color]
        > the[color=green]
        > > data where i get all the children of, say, ID=1 and all the children of[/color][/color]
        ID[color=blue]
        > =[color=green]
        > > 4.
        > > What would be the best way to achieve the above using MySQL db and php?
        > >
        > > If i read all the data sorted by PARENT i might be able to read the[/color][/color]
        whole[color=blue][color=green]
        > > table at once and add all the data to one array?
        > >
        > > Any ideas?
        > >
        > > Regards.
        > > Simon/
        > >[/color][/color]
        think he wants arrays inside arrays... to output.. something like this would
        work

        foreach($data['array of some sort'] as $key => $value)

        {

        if(is_array($va lue))

        {

        foreach($value as $key1 => $value1)

        {

        if(is_array($va lue1))

        {

        foreach($value1 as $key2 => $value2)

        {

        do something with $value2

        }

        }

        else { do something with $value1}

        }

        }

        else {do something with $value}

        }

        not the best way of doing thing but that should get you 3 deep, sure ya see
        whats happening


        Comment

        • Sims

          #5
          Re: Help needed to build an array

          Hi,

          [color=blue]
          > think he wants arrays inside arrays... to output.. something like this[/color]
          would[color=blue]
          > work
          >[/color]

          <snip code>
          [color=blue]
          >
          > not the best way of doing thing but that should get you 3 deep, sure ya[/color]
          see[color=blue]
          > whats happening
          >[/color]

          Thanks but i do not know how deep it goes, maybe that is what i should use a
          class.
          Where class definition is something like

          class ITEMS
          {
          var $iParent = // int id of parent or -1 if no parent
          var $aChildren = // array of class ITEMS or false if no children

          // and some functions like
          function GetChild( $id )
          {
          // return the array all the children
          }
          }

          Or something like that.
          But i would i build the class.

          Simon.


          Comment

          • Shawn Wilson

            #6
            Re: Help needed to build an array

            Sims wrote:[color=blue]
            >
            > Hi
            >
            > I have a table with something like
            >
            > ID PARENT
            >
            > 0 | -1
            > 1 | -1
            > 2 | 1
            > 3 | 1
            > 4 | 2
            > 5 | -1
            > 6 | 4
            >
            > And i want to build an array so i can output the data in the form
            >
            > 0
            > 1
            > |--2
            > |----4
            > | |----5
            > |--3
            > 5
            >
            > Where 2 is a child of 1, and 4 is a child of 2 and so on.
            > I could create an array like $data[$id][$parent] but how would i output the
            > data where i get all the children of, say, ID=1 and all the children of ID =
            > 4.
            > What would be the best way to achieve the above using MySQL db and php?
            >
            > If i read all the data sorted by PARENT i might be able to read the whole
            > table at once and add all the data to one array?[/color]

            Try a recursive function and 2 arrays, passed by reference.
            Arrays: oldarray()(cont aining table results) and newarray() (empty)

            function makelist(& $oldarray,& $newarray, $id) {
            //go through old array, searching for anything with parent $id
            //if found, add to new array in correct place, delete from old array and call
            makelist with new id
            }

            Start your function off with $id=-1.
            The actual code is a bit trickier than the comments.
            Consider what happens if:
            -parent doesn't exist
            -there are >1 children - how do you suborder them?
            -there's a loop (id=>1, parent=>2)(id=> 2,parent=>1) //should never happen

            Anyway, that should order your stuff.
            For echoing the results, you could write a function getindent($id)

            function getindent($id, $newarray) {
            $indent=0;
            $foundit=0;

            foreach($newarr ay as $foo){
            if ($foo['id'] == $id) {
            $parent=$foo['parent'];
            if ($parent == -1)
            return $indent;
            break;
            }
            }

            while ($foundit==0) {
            foreach($newarr ay as $foo){
            if ($parent == $foo['id']) {
            $indent++;
            if ($foo['parent'] == -1)
            return $indent;
            $parent = $foo['parent'];
            break;
            }
            }
            }
            }

            This function is untested and likely contains typos and/or small logic errors.
            It does not have any failsafes (if an array element has the id of a non-existant
            parent or if there's a loop in the parents, as above, it will loop until the
            script times out). If you use it, I suggest you improve it.

            Then to display:

            foreach($newarr ay as $foo) {
            $indents = getindent(-1, $newarray);
            for($i=0;$i<$in dents;++$i)
            echo '-';
            echo $foo['id']."<br>";
            }

            Regards,
            Shawn
            --
            Shawn Wilson
            shawn@glassgian t.com

            Comment

            • Erik Johnson

              #7
              Re: Help needed to build an array

              I would strongly disagree with Mr. Smith's broad assertion that children
              and parents aren't used in arrays. Arrays are a tool to serve their master.
              If I am understanding the goal here, you want to map a parent id to an array
              of children id's. Array elements can themselves be arrays, so this is no big
              deal. You call the database, say with something like "select * from parent",
              and you get back all the rows in your table.

              You then iterate through each row in the table, building up your data
              structure (I'm assuming -1 is being used here to represent no parent).

              #set $n_rows to the number of rows in your table
              for ($i = 0; $i < $n_rows; $i++)
              {
              # get your parent id poked into $pid, child id poked into $cid
              if ($pid != -1)
              $data[$pid][] = $cid;
              }

              $data then is built as a 2-D array and comes out looking like:
              $data[1] = array(2, 3);
              $data[2] = array(4);
              $data[4] = array(6);

              The formatted output you show below doesn't make any sense to me, so
              I'll leave that part to you, but given a parent id, $data maps to an array
              of children ID - that is the crux of your issue as I understand it.

              Just FYI, this looks like a relatively expensive thing to do - I don't
              know anything about caching data from one page invocation to the next, but
              unless you have some sort of a caching mechanism you are (potentially)
              downloading this whole table and building your mapping on every page
              request. Maybe this is in a standalone script so it doesn't matter, or maybe
              you don't care about performance anyway - but just something to consider.

              HTH,
              -ej


              "Sims" <siminfrance@ho tmail.com> wrote in message
              news:c1vqsh$1mo l76$1@ID-162430.news.uni-berlin.de...[color=blue]
              > Hi,
              >
              > "John Smith" <someone@nobody .com> wrote in message
              > news:c1vq20$ro9 $1@news3.tilbu1 .nb.home.nl...[color=green]
              > > Children and Parents aren't used in Arrays, are you using Objects or
              > > Arrays???
              > >[/color]
              >
              > I am not using anything yet, i just want to know what would be the best[/color]
              way[color=blue]
              > to read the data
              > so that i can get the children(s) of all ids.
              >
              > It could be a class i guess, I want a function that would read the data[/color]
              from[color=blue]
              > the database and build all the parents recursively so that i could, for
              > example, get all the children for ID = 1 and i would return 2, 3.
              >
              > I want to build the array/class in one call of the database and not all
              > every time i need to find the child of an ID.
              >[color=green][color=darkred]
              > > > ID PARENT
              > > >
              > > > 0 | -1
              > > > 1 | -1
              > > > 2 | 1
              > > > 3 | 1
              > > > 4 | 2
              > > > 5 | -1
              > > > 6 | 4
              > > >
              > > > And i want to build an array so i can output the data in the form
              > > >
              > > > 0
              > > > 1
              > > > |--2
              > > > |----4
              > > > | |----5
              > > > |--3
              > > > 5
              > > >
              > > > Where 2 is a child of 1, and 4 is a child of 2 and so on.
              > > > I could create an array like $data[$id][$parent] but how would i[/color][/color][/color]
              output[color=blue][color=green]
              > > the[color=darkred]
              > > > data where i get all the children of, say, ID=1 and all the children[/color][/color][/color]
              of[color=blue]
              > ID[color=green]
              > > =[color=darkred]
              > > > 4.
              > > > What would be the best way to achieve the above using MySQL db and[/color][/color][/color]
              php?[color=blue][color=green][color=darkred]
              > > >
              > > > If i read all the data sorted by PARENT i might be able to read the[/color][/color]
              > whole[color=green][color=darkred]
              > > > table at once and add all the data to one array?
              > > >
              > > > Any ideas?
              > > >
              > > > Regards.
              > > > Simon/
              > > >
              > > >[/color]
              > >
              > >[/color]
              >
              >[/color]


              Comment

              • Sims

                #8
                Re: Help needed to build an array

                [color=blue]
                > I would strongly disagree with Mr. Smith's broad assertion that[/color]
                children[color=blue]
                > and parents aren't used in arrays. Arrays are a tool to serve their[/color]
                master.[color=blue]
                > If I am understanding the goal here, you want to map a parent id to an[/color]
                array[color=blue]
                > of children id's. Array elements can themselves be arrays, so this is no[/color]
                big[color=blue]
                > deal. You call the database, say with something like "select * from[/color]
                parent",[color=blue]
                > and you get back all the rows in your table.[/color]

                i tend to agree with you. Arrays might be the right thing for me.
                But an object might also do the trick, i think.
                [color=blue]
                >
                > You then iterate through each row in the table, building up your data
                > structure (I'm assuming -1 is being used here to represent no parent).
                >[/color]

                <snip code >

                All i want is to call the database, "select * from table1"
                and then build some form of array/object that will contain
                1) It's own ID number
                2) The number of it's father, (-1 been no father).

                So looking at it like that i could create a class

                class DATA_1{
                $father;
                $number;
                }

                class DATA_2{
                $data_1 = array(); // of class data_1
                }

                fill the array using a select.

                but then how would i output it?
                maybe somerecuring function...like

                // $data_2 is class DATA_2
                function print_tree( $depth, $id )
                {
                // output the $id using the depth
                $data = $data_2->GetChildren( -1 ); would return all the item whose
                parent is -1;
                foreach( $data as $x ){
                print_tree( ($depth+1), $x );
                }
                }

                So the output would print all the father followed by all the children's...

                i would start the loop with
                print_tree( 0, -1 )

                I think...
                And that way i would only call the DB once to build the array.
                [color=blue]
                >
                > The formatted output you show below doesn't make any sense to me, so
                > I'll leave that part to you, but given a parent id, $data maps to an array
                > of children ID - that is the crux of your issue as I understand it.[/color]

                The formatted thing was just to try to explain what i was after.

                [color=blue]
                >
                > Just FYI, this looks like a relatively expensive thing to do - I don't
                > know anything about caching data from one page invocation to the next, but
                > unless you have some sort of a caching mechanism you are (potentially)
                > downloading this whole table and building your mapping on every page
                > request. Maybe this is in a standalone script so it doesn't matter, or[/color]
                maybe[color=blue]
                > you don't care about performance anyway - but just something to consider.[/color]

                Yes you are right but it is only used in one page, (for the administrator to
                check that the data are still in good order).
                And secondly it is only a 10/20 items table max.

                But i am always looking for better ways to do things, if you know of a
                better way...

                Simon.



                Comment

                • Erik Johnson

                  #9
                  Re: Help needed to build an array


                  "Sims" <siminfrance@ho tmail.com> wrote in message
                  news:c207vb$1nh 8on$1@ID-162430.news.uni-berlin.de...
                  [color=blue]
                  > All i want is to call the database, "select * from table1"
                  > and then build some form of array/object that will contain
                  > 1) It's own ID number
                  > 2) The number of it's father, (-1 been no father).[/color]

                  This is a *different* (but still trivial) problem. Here's an array
                  based solution:

                  #set $n_rows to the number of rows in your table
                  for ($i = 0; $i < $n_rows; $i++)
                  {
                  # get your parent id poked into $pid, child id poked into $cid
                  $data[$cid] = $pid;
                  }


                  The second part, the question that you are hinting at but haven't asked
                  directly is

                  "How do I pretty print a textual representation of a general tree?"

                  That's a very non-trivial problem. In fact, there is nothing here that
                  even implies a true tree (i.e., there is nothing preventing you from
                  creating loops in your parent-child table). In the general case, each node
                  can (recursively) have any number of children. So, I don't have an easy
                  answer for how you are going to pretty-print that. That doesn't mean it's
                  impossible to do, just that it's very non-trivial. If you just need to see
                  the information, go back to my first solution, and recursively iterate
                  through the keys and print lines like:

                  parent0: {}
                  parent1: {child2, child3}
                  parent2: {child4}
                  parent3: {}
                  parent4: {child6}
                  parent5: {}
                  parent6: {}

                  Or use the solution in this post, and print lines like:

                  child0: NO-parent
                  child1: NO-parent
                  child2: parent1
                  ....

                  For a given node, you will have to trace the lineage through several
                  lines. But this is essentially just dumping your table.

                  If you are serious about solving the harder problem, pretty-printing a
                  general tree, first come up with a textual representation that addresses the
                  general case. It's silly to waste time taking pot-shots in the dark at code
                  fragments that sorta-might-maybe-kinda help with a piece of the problem
                  without first understanding the ultimate goal.

                  -ej


                  Comment

                  • John Smith

                    #10
                    Re: Help needed to build an array


                    "Erik Johnson" <ej@just.post.h ere.com> schreef in bericht
                    news:4044cf1b$1 @news.zianet.co m...[color=blue]
                    >
                    > "Sims" <siminfrance@ho tmail.com> wrote in message
                    > news:c207vb$1nh 8on$1@ID-162430.news.uni-berlin.de...
                    >[color=green]
                    > > All i want is to call the database, "select * from table1"
                    > > and then build some form of array/object that will contain
                    > > 1) It's own ID number
                    > > 2) The number of it's father, (-1 been no father).[/color]
                    >
                    > This is a *different* (but still trivial) problem. Here's an array
                    > based solution:
                    >
                    > #set $n_rows to the number of rows in your table
                    > for ($i = 0; $i < $n_rows; $i++)
                    > {
                    > # get your parent id poked into $pid, child id poked into $cid
                    > $data[$cid] = $pid;
                    > }
                    >
                    >
                    > The second part, the question that you are hinting at but haven't[/color]
                    asked[color=blue]
                    > directly is
                    >
                    > "How do I pretty print a textual representation of a general tree?"
                    >
                    > That's a very non-trivial problem. In fact, there is nothing here that
                    > even implies a true tree (i.e., there is nothing preventing you from
                    > creating loops in your parent-child table). In the general case, each node
                    > can (recursively) have any number of children. So, I don't have an easy
                    > answer for how you are going to pretty-print that. That doesn't mean it's
                    > impossible to do, just that it's very non-trivial. If you just need to see
                    > the information, go back to my first solution, and recursively iterate
                    > through the keys and print lines like:
                    >
                    > parent0: {}
                    > parent1: {child2, child3}
                    > parent2: {child4}
                    > parent3: {}
                    > parent4: {child6}
                    > parent5: {}
                    > parent6: {}
                    >
                    > Or use the solution in this post, and print lines like:
                    >
                    > child0: NO-parent
                    > child1: NO-parent
                    > child2: parent1
                    > ...
                    >
                    > For a given node, you will have to trace the lineage through several
                    > lines. But this is essentially just dumping your table.
                    >
                    > If you are serious about solving the harder problem, pretty-printing a
                    > general tree, first come up with a textual representation that addresses[/color]
                    the[color=blue]
                    > general case. It's silly to waste time taking pot-shots in the dark at[/color]
                    code[color=blue]
                    > fragments that sorta-might-maybe-kinda help with a piece of the problem
                    > without first understanding the ultimate goal.
                    >
                    > -ej
                    >
                    >[/color]
                    Beware if you're using a loop to print trees, you might get an infinite
                    (recursive) loop.
                    e.g.
                    1 points to 2
                    2 points to 4
                    4 points to 3
                    3 points to 1

                    Nice to mention is print_r()
                    It had the same problem, although it's solved now, try print_r($_GLOBA LS);




                    Comment

                    • John Smith

                      #11
                      Re: Help needed to build an array


                      "Sims" <siminfrance@ho tmail.com> schreef in bericht
                      news:c1vrq6$1mv 0j7$1@ID-162430.news.uni-berlin.de...[color=blue]
                      > Hi,
                      >
                      >[color=green]
                      > > think he wants arrays inside arrays... to output.. something like this[/color]
                      > would[color=green]
                      > > work
                      > >[/color]
                      >
                      > <snip code>
                      >[color=green]
                      > >
                      > > not the best way of doing thing but that should get you 3 deep, sure ya[/color]
                      > see[color=green]
                      > > whats happening
                      > >[/color]
                      >
                      > Thanks but i do not know how deep it goes, maybe that is what i should use[/color]
                      a[color=blue]
                      > class.
                      > Where class definition is something like
                      >
                      > class ITEMS
                      > {
                      > var $iParent = // int id of parent or -1 if no parent
                      > var $aChildren = // array of class ITEMS or false if no[/color]
                      children[color=blue]
                      >
                      > // and some functions like
                      > function GetChild( $id )
                      > {
                      > // return the array all the children
                      > }
                      > }
                      >
                      > Or something like that.
                      > But i would i build the class.
                      >
                      > Simon.
                      >
                      >[/color]
                      Maybe this will help
                      WARNING untested script so beware of typos and other bad stuff.

                      $prefix='';
                      $maintree=array ();

                      print_tree($mai ntree,$prefix)

                      function print_tree($tre e,$prefix)
                      {
                      if(is_array($tr ee))
                      {
                      foreach($tree as $newtree)
                      {
                      print_tree($new tree,$prefix.'---');
                      }
                      }
                      else echo $prefix.$tree." <br />\r\n";
                      }


                      Comment

                      Working...