Dominyc Turner
Dominyc Turner

Reputation: 11

PHP how to add integers together from for loop

I have 2 arrays. One for letters and for points of said letter.

I've gotten the user input word and turned it into an array.

I then loop through the $letters array to find the key of each letter in the word.

Next I loop through the $points array to find the value of key that corresponds to the position of the letter. The problem I'm having is that when I find the values, I want to add them together but I can't. array_sum() gives an error saying it must be an array.

Here is my code:

<?php
$letters = ["A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", "ER", "CL", "IN", "TH", "QU"];

$points= [2, 8, 8, 5, 2, 6, 6, 7, 2, 13, 8, 3, 5, 5, 2, 6, 15, 5, 3, 3, 4, 11, 10, 12, 4, 14, 7, 10, 7, 9, 9];

if(isset($_POST['play'])) {
    //INDEX TO COUNT THROUGH 'letters' ARRAY
    $spot = "";
    $tally = 0;
    //GET WORD FROM USER AND UPPERCASE IT
    $ply1_word = strtoupper($_POST['player1']);
    //TURN WORD STRING INTO ARRAY
    $word_letters = str_split($ply1_word);
//    echo "<pre>";
//    print_r($word_letters);
//    echo "</pre>";
    for ($i = 0; $i < count($word_letters); $i++)  {
        if (in_array($word_letters[$i], $letters)) {
            $spot = array_search($word_letters[$i], $letters);
        }
        if (isset($values[$spot])) {
//            echo $values[$spot] . "<br>";
//            print_r($values[$spot]);
//            var_dump($values[$spot]);
//  NEED TO ADD NUMBERS TOGETHER HERE OR AFTER HERE
        }
    }
}

Upvotes: 0

Views: 517

Answers (3)

Bjorn
Bjorn

Reputation: 5362

The points raised by @micster are very true. Just to give you an idea of how this problem could be solved in a totally different way (using array_reduce):

<?php

$scores = [
    "A" => 2, "B" => 8, "C" => 8, "D" => 5, "E" => 2, 
    "F" => 6, "G" => 6, "H" => 7, "I" => 2, "J" => 13, 
    "K" => 8, "L" => 3, "M" => 5, "N" => 5, "O" => 2, 
    "P" => 6, "Q" => 15, "R" => 5, "S" => 3, "T" => 3, 
    "U" => 4, "V" => 11, "W" => 10, "X" => 12, "Y" => 4, 
    "Z" => 14, "ER" => 7, "CL" => 10, "IN" => 7, "TH" => 9, 
    "QU" => 9,
];

$word = 'thesaurus';

$wordScore = array_reduce(str_split($word, 2), function($carriedScore, $charPair) use ($scores) {
    $charPair = strtoupper($charPair);

    if(isset($scores[$charPair])) {
        $score = $scores[$charPair];
    } else {
        $score = $scores[$charPair[0]] ?? 0;
        $score += $scores[$charPair[1]] ?? 0;
    }

    return $carriedScore + $score;
}, 0);

var_dump($wordScore); // 32

The general idea behind this code is that we first split the entered word into two-character combinations. So following the example, we're creating an array: [ th, es, au, ru, s ]. Then, per item, we're checking if the combination exists in our $scores array. If not, we're just combining the scores of the individual chars.

There is still one flaw left in this code. If your word is tenth ([ te, nt, h ]), it will be scored as t+e+n+t+h and not t+e+n+th.

Upvotes: 0

micster
micster

Reputation: 758

You got some issues in your code :

  • you are using $values wich doesn't exists, you should replace it with $points.
  • you add points even if the character isn't in your $letters (try with "test me"), the space add points related to T.
  • your code can't handle your last letters ("ER", "CL", "IN", "TH", "QU")

You can do this without using array_sum, with += :

$tally += $points[$spot]

And to go further, your code can't handle the last $letters, you need to change your code to check these letters too.

Working code, with some var_dump :

if(isset($_POST['play'])) {
    $spot = "";
    $tally = 0;
    //GET WORD FROM USER AND UPPERCASE IT
    $ply1_word = strtoupper($_POST['player1']);
    var_dump($ply1_word);
    //TURN WORD STRING INTO ARRAY
    $word_letters = str_split($ply1_word);
    print_r($word_letters);
    $skipNextLetter = false; // needed to handle "ER", "CL", "IN", "TH", "QU"
    for ($i = 0; $i < count($word_letters); $i++)  {
        // reset $spot to prevent adding points when char isn't in $letters
        $spot = '';
        // don't check this char if old one was a combination of two chars
        if ($skipNextLetter) {
            $skipNextLetter = false;
            continue;
        }
        $char = $word_letters[$i];
        $charTemp = $word_letters[$i];
        // handle "ER", "CL", "IN", "TH", "QU"
        if (isset($word_letters[$i + 1])) {
            $charTemp .= $word_letters[$i + 1];
            var_dump('===> check with next char :: ' . $charTemp);
            if (in_array($charTemp, ['ER', 'CL', 'IN', 'TH', 'QU'])) {
                $char = $charTemp;
                $skipNextLetter = true;
            }
        }
        if (in_array($char, $letters)) {
            $spot = array_search($char, $letters);
        }
        var_dump('CHAR => ' . $char . ' / SPOT => ' . $spot);
        if (isset($points[$spot])) {
           echo $points[$spot] . "<br>";
        //    print_r($points[$spot]);
           var_dump('ADDING POINTS : ' . $points[$spot]);
//  NEED TO ADD NUMBERS TOGETHER HERE OR AFTER HERE
            $tally += $points[$spot];
        }
    }

Results :

$test = 'Stackoverflow';
// $tally = 65
$test = 'Stackoverflow Clean';
// $tally = 84

As Fritz said, I would have done things in a different way (ie. with array_values)

Upvotes: 1

Fritz Bester
Fritz Bester

Reputation: 172

Your code (as it is) nearly works.

There are only a couple of fixes you need to add.

Where it reads:

 if (isset($values[$spot])) {

You don't have a $values variable declared anywhere, so I'm assuming you meant:

 if (isset($points[$spot])) {

Lastly, to total the actual point values, you can use the following (after fixing the above line):

if (isset($points[$spot])) {
    $tally += $points[$spot];
}

So all in all:

<?php
$letters = ["A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", "ER", "CL", "IN", "TH", "QU"];

$points= [2, 8, 8, 5, 2, 6, 6, 7, 2, 13, 8, 3, 5, 5, 2, 6, 15, 5, 3, 3, 4, 11, 10, 12, 4, 14, 7, 10, 7, 9, 9];

if(isset($_POST['play'])) {
    //INDEX TO COUNT THROUGH 'letters' ARRAY
    $spot = "";
    $tally = 0;
    //GET WORD FROM USER AND UPPERCASE IT
    $ply1_word = strtoupper($_POST['player1']);
    //TURN WORD STRING INTO ARRAY
    $word_letters = str_split($ply1_word);
//    echo "<pre>";
//    print_r($word_letters);
//    echo "</pre>";
    for ($i = 0; $i < count($word_letters); $i++)  {
        if (in_array($word_letters[$i], $letters)) {
            $spot = array_search($word_letters[$i], $letters);
        }
        if (isset($points[$spot])) {
//            echo $values[$spot] . "<br>";
//            print_r($values[$spot]);
//            var_dump($values[$spot]);
//  NEED TO ADD NUMBERS TOGETHER HERE OR AFTER HERE
              $tally += $points[$spot];
        }
    }
    // Maybe print the Word and tally here?
    echo $ply1_word . " has score of " . $tally . "<br>";


}

That being said, I would have done things quite differently.

For starters, I would have used an associative array where the Characters are the Keys and the Points are the values.

Nevertheless, your solution is workable as long as you fix the above errors.

Regards, Fritz.

Upvotes: 0

Related Questions