Sortierung von Arrays - Ausgabe bei gleichem Wert

Einklappen
X
 
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

  • Sortierung von Arrays - Ausgabe bei gleichem Wert

    Hallo,

    ich habe ein Array $spieler mit Namen als Schlüssel und eine Punktzahl als Wert.

    also z.b.

    $spieler["Playaa"] = 4;
    $spieler["Spiel0r"] = 3;

    usw.

    Jetzt möchte ich die Namen, sortiert nach der erreichten Punktzahl, untereinander ausgeben und dabei aber noch die Platzierung anzeigen lassen.

    z.B.:
    Code:
    +--- Platz  |  Name    | Gesamtpunktzahl ---+
    |      1       Playaa            4          |
    |      2       Spiel0r           3          |
    +-------------------------------------------+
    Das habe ich im Moment so gelöst:

    PHP-Code:
    <?php

    echo "<table>";

    arsort($spieler); // nach punkten absteigend sortieren
    $platz 1;      

    foreach(
    $spieler as $spielername => $punkte)
    {
      echo 
    "<tr>";
        echo 
    "<td align='center'>".$platz."</td>";
        echo 
    "<td>".$spielername."</td>";
        echo 
    "<td align='center'>".$punkte."</td>";
      echo 
    "</tr>";
            
      
    $platz++; // Platz fuer naechste Zeile erhoehen
            
    }

    echo 
    "</table>";
    ?>
    Doch, wenn zwei oder mehr Spieler dieselbe Punktzahl erreicht haben, soll auch derselbe Platz ausgegeben werden, also z.B.

    Code:
    +--- Platz  |  Name    | Gesamtpunktzahl ---+
    |      1-2     Playaa            4          |
    |      1-2     Spiel0r           4          |
    +-------------------------------------------+
    Wie lässt sich das am besten lösen?

    Vielen Dank für eure Hilfe und freundliche Grüße
    Boron

  • #2
    Re: Sortierung von Arrays - Ausgabe bei gleichem Wert

    Merke dir am Ende der Schleife die Punktzahl des Spielers - und vergleiche dann im nächsten Durchlauf diesen Wert mit dem aktuellen. Und falls die gleich sind, wird der Platz-Zähler eben nicht erhöht.

    Überlege dir dabei, wie der Sonderfall "erster Schleifendurchlauf", in dem es noch keinen vorherigen Wert gibt, sinnvoll zu behandeln ist.


    Und gängig bei solchen Zählungen dürfte außerdem sein, dass wenn zwei Spieler auf Platz 4 landen, dann der nächste Platz nicht als 5, sondern aus 6 ausgewiesen wird, bzw. bei mehr Gleichplatzierten dann analog weiter hochgezählt.
    Es könnte also auch noch sinnvoll sein mitzuzählen, wie viele gleichplatzierte jeweils aufeinanderfolgen, um dann den Platz-Zähler anschließend gleich um diesen Wert zu erhöhen.
    I don't believe in rebirth. Actually, I never did in my whole lives.

    Kommentar


    • #3
      Ich habe deine Variante versucht, aber konnte es irgendwie nicht erfolgreich umsetzen.

      Ich habe eine andere Möglichkeit probiert - mit Hilfe eines weiteren Arrays, das die Anzahl an vorhanden Punkten beinhaltet:

      PHP-Code:
      <?php
      arsort
      ($spieler); // nach punkten absteigend sortieren
            
      $scores = array();
      foreach(
      $spieler as $spielername => $punkte)
      {
        
      $punkte strval($punkte); // strval, da u.a. fliesskommazahlen
              
        
      if(array_key_exists($punkte$scores))
        {
          
      $scores[$punkte] = $scores[$punkte] + 1;
        }
        else
        {
          
      $scores[$punkte] = 1;
        }
      }


      $zeile 1;      
      $platz 1;

      foreach(
      $spieler as $spielername => $punkte)
      {
        
      $punkte strval($punkte);
        
        echo 
      "<tr>";
          echo 
      "<td align='center'>";
          
          if(
      $scores[$punkte] != 1)
          {
            echo 
      intval($platz)." - ".intval($platz $scores[$punkte] - 1);
          }
          else
          {
            
      $platz $zeile;
            echo 
      $platz;
          }
               
          echo 
      "</td>";
          echo 
      "<td>".urldecode($spielername)."</td>";
          echo 
      "<td align='center'>".$punkte."</td>";
        echo 
      "</tr>";
              
        
      $zeile++;
          
      }
      ?>
      Die Arrays $scores und $spieler sind soweit korrekt. Das Problem ist jetzt, wenn ich zwei Mal hintereinander Spieler habe, die dieselbe Punktzahl haben, wird die $platz Variable nicht erhöht. Somit wird eine falsche Platzierung angezeigt.

      Also meine Ausgabe im Moment lautet (dadurch fehlerhaft) beispielsweise:
      Code:
      +-- Platz    |      Name       |  Gesamtpunktzahl ---+
      |                                                    |
      |     1-2         Spielaa                5.5         |
      |     1-2         Playaaa                5.5         |
      |      3             No3                  4          |
      |     4-5         EinName                3.5         |
      |     4-5           N.N.                 3.5         |
      |     4-5        HierDerFehler            3          |
      |     4-5           JaJa...               3          |
      +-----------------------------------------------------+
      Wie lässt sich das ändern?

      Kommentar


      • #4
        UPDATE:

        Tutet so:

        PHP-Code:
        <?php
        arsort
        ($spieler); // nach punkten absteigend sortieren
              
              
        $scores = array();
        foreach(
        $spieler as $spielername => $punkte)
        {
          
        $punkte strval($punkte); // strval, da fliesskommazahlen
                
          
        if(array_key_exists($punkte$scores))
          {
            
        $scores[$punkte] = $scores[$punkte] + 1;
          }
          else
          {
            
        $scores[$punkte] = 1;
          }
        }


        $zeile 1;      
        $platz 1;
        $prevPunkte = -1;

        foreach(
        $spieler as $spielername => $punkte)
        {
          
        $punkte strval($punkte);
          
          echo 
        "<tr>";
            echo 
        "<td align='center'>";
            
           if(
        $punkte != $prevPunkte)
           {
              
        $platz $zeile;
           }

           
        $prevPunkte $punkte;

            if(
        $scores[$punkte] != 1)
            {
              echo 
        intval($platz)." - ".intval($platz $scores[$punkte] - 1);
            }
            else
            {
              echo 
        $platz;
            }
                 
            echo 
        "</td>";
            echo 
        "<td>".urldecode($spielername)."</td>";
            echo 
        "<td align='center'>".$punkte."</td>";
          echo 
        "</tr>";
                
          
        $zeile++;
            
        }
        ?>

        Kommentar


        • #5
          irgendwie sieht das unnötig kompliziert aus...
          wieso denn nicht so:

          PHP-Code:
          echo "<table>";

          arsort($spieler); // nach punkten absteigend sortieren
          $platz 1;
          $letzte_punkte = -1;

          foreach(
          $spieler as $spielername => $punkte)
          {
            echo 
          "<tr>";
              echo 
          "<td align='center'>".$platz."</td>";
              echo 
          "<td>".$spielername."</td>";
              echo 
          "<td align='center'>".$punkte."</td>";
            echo 
          "</tr>";
            
            if (
          $letzte_punkte != $punkte) {
                
          $platz++; // Platz fuer naechste Zeile erhoehen
            
          }
              
            
          $letzte_punkte $punkte;    
          }

          echo 
          "</table>"

          Kommentar


          • #6
            Weil einerseits bei "gleichplatzierten" Spielern nicht deutlich wird, um welchen Bereich es geht (Platz "4 bis 6") und weil andererseits nach gleichplatzierten Spielern der Platzzähler nur um eins erhöht wird, was aber unlogisch ist. Ausgabe sähe dann so aus

            Platz | Name
            4 Spieler A
            4 Spieler B
            4 Spieler C
            5 Spieler D


            Natürlich gibt es noch andere Möglichkeiten mein o.g. Problem zusetzen, z.B.

            PHP-Code:
            <?php

            arsort
            ($spieler); // nach punkten absteigend sortieren
                  
            $scores = array();
            foreach(
            $spieler as $spielername => $punkte)
            {
              
            $punkte strval($punkte); // strval, da fliesskommazahlen
                    
              
            if(array_key_exists($punkte$scores))
              {
                
            $scores[$punkte][] = $spielername;
              }
              else
              {
                
            $scores[$punkte] = array();
                
            $scores[$punkte][] = $spielername;
              }
            }

                  
            $position 1;      

            foreach(
            $scores as $score => $playerList)
            {
                if( 
            count($playerList) == ) {
                    
            $string $position;
                }
                else {
                    
            $string $position ' - ' . ($position count($playerList) - 1);
                }
                
                foreach(
            $playerList as $player)
                {
                    echo 
            "<tr>";
                    echo 
            "<td align='center'>";
                    echo 
            $string;
                     echo 
            "</td>";
                    echo 
            "<td>".urldecode($player)."</td>";
                    echo 
            "<td align='center'>".$score."</td>";
                  echo 
            "</tr>";
                }
              
                  
            $position += count($playerList);  
            }

            ?>

            Kommentar


            • #7
              Original geschrieben von Boron
              Weil einerseits bei "gleichplatzierten" Spielern nicht deutlich wird, um welchen Bereich es geht (Platz "4 bis 6")
              Solch eine Anzeige finde ich unlogisch, bzw. habe ich eigentlich noch nie gesehen.

              Wenn die drei Spieler punktgleich sind, dann gibt es drei erste Plätze - und danach folgt der vierte.
              und weil andererseits nach gleichplatzierten Spielern der Platzzähler nur um eins erhöht wird, was aber unlogisch ist.
              Das hättest du aber mit meinem Vorschlag eines zusätzlichen Zählers, wie viele Spieler nacheinander auf dem gleichen Platz landen, leicht auch in Markus' Script implementieren können.
              I don't believe in rebirth. Actually, I never did in my whole lives.

              Kommentar

              Lädt...
              X