skip to Main Content

I have an array with two values $arr = ['up', 'down'];. If someone casts an up vote ($vote = 'up';) the up field should be increased by one and the down field should be decreased by one in the database.

I could work with an if else condition:

if ($vote === 'up') {
  $voteModel['up'] = $voteModel['up'] + 1;
  $voteModel['down'] = $voteModel['down'] - 1;
} else {
  $voteModel['up'] = $voteModel['up'] - 1;
  $voteModel['down'] = $voteModel['down'] + 1;
}

But I’m wondering if this can be made shorter. I was thinking of an arr = ['up' => 'down']; but unfortunately I’m not getting anywhere with that right now. Do you have any ideas? Thank you!

5

Answers


  1. You can simplify it by using some reference data. Use $vote value to find an entry in the $voteVals array telling it what values to increase and decrease by in each case. Then simply loop through the vote model, and action each entry by updating by the amount specified in the reference data. Matching is done simply using the "up" and "down" string values:

    $voteVals = ["up" => ["up" => 1, "down" => -1], "down" => ["up" => -1, "down" => 1]];
    $voteModel = ["up" => 0, "down" => 0];
    $vote = "up";
    
    $voteActionVals = $voteVals[$vote];
    
    foreach ($voteActionVals as $key => $val)
        $voteModel[$key] += $val;
    
    var_dump($voteModel);
    

    Output:

    array(2) {
    ["up"]=>
    int(1)
    ["down"]=>
    int(-1)
    }

    As you can see, this has incremented the "up" entry by 1 and decremented the "down" value by 1.

    Live demo: https://3v4l.org/9oFHH

    Login or Signup to reply.
  2. Solution 1:

    $arg = $vote === 'up' ? [1,-1] : [-1,1];
    $voteModel['up'] += $arg[0];
    $voteModel['down'] += $arg[1];
    

    Solution 2:

    $voteModel['up'] += ($vote === 'up' ? 1 : -1);
    $voteModel['down'] += ($vote !== 'up' ? 1 : -1);
    

    Solution 3 (if ‘up’ is index 1 and ‘down’ is index 0 in $voteModel):

    $voteModel[$vote==='up']++;
    $voteModel[$vote==='down']--;
    

    Solution 3b (if we want to keep the assoc keys):

    $arr = ['down','up'];
    $voteModel[$arr[$vote==='up']]++;
    $voteModel[$arr[$vote==='down']]--;
    
    Login or Signup to reply.
  3. The scoring system has two general methods.

    1- Showing the number of positive votes and showing negative votes. Positive votes do not cancel out negative votes and negative votes do not cancel out positive votes. Like YouTube

    2- Display the total number of votes as if you have a column of votes in the database. A positive score adds one to it and a negative score subtracts one from it.

    So, for you who use the first mode, it is not necessary to add it to the scoring system in the case of a positive one and subtract one from it in the case of a negative score.

    you can use this code

    
    $voteModel['up'] += $vote === 'up' ? 1 : -1;
    $voteModel['down'] += $vote !== 'up' ? 1 : -1;
    
    
    Login or Signup to reply.
  4. <?php
    function vote($model, $vote) {
        $up = $vote === 'up' ? 1 : -1;
        $model['up'] +=  $up;
        $model['down'] -= $up;
        return $model;
    }
    
    $voteModel = [
            'up' => 5,
            'down' =>5
    ];
    
    
    print_r(vote($voteModel, 'up'));
    
    print_r(vote($voteModel, 'down'));
    

    https://phpize.online/sql/mysql57/undefined/php/php81/77d709373d4e930e0e0113c11984e0b8/

    One more:

    function vote($model, $vote) {
        foreach($model as $key=>$val){
            $model[$key] = $val + ($vote === $key ? 1 : -1);
        }
        return $model;
    }
    
    Login or Signup to reply.
  5. Although you’ve asked for shorter, sometimes I think clarity is better. Most of the other answers include additional arrays or ternaries, which are totally fine and 100% valid, but I think the intention of the code isn’t as obvious then. For me, I’d keep the if and just use ++ and -- for increment and decrement. I think the "business rules" are very obvious and the code reads cleanly.

    Once again, not exactly what you asked for, just my two cents.

    if ('up' === $vote) {
        $voteModel['up']++;
        $voteModel['down']--;
    } else {
        $voteModel['up']--;
        $voteModel['down']++;
    }
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search