0

I am trying to write a Star-rating function in PHP to return the result (not just echo it).

My newer version is:

function getRating($rating, $ret = '') {
    if ($rating == 0) { return $ret; }
    if ($rating < 1) {
        $ret .= '<span class="fa fa-star-half-empty"></span>';
        $rating-= 0.5;
    } else {
        $ret .= '<span class="fa fa-star"></span>';
        $rating-= 1;
    }
    getRating($rating, $ret);
}
$var = getRating(5.0);

This returns null. The older version just echo it but I want it to hold the rating in a variable:

function getRating($rating,) {
    if ($rating == 0) { return; }
    if ($rating < 1) {
        echo '<span class="fa fa-star-half-empty"></span>';
        $rating-= 0.5;
    } else {
        echo '<span class="fa fa-star"></span>';
        $rating-= 1;
    }
    getRating($rating);
}
getRating(5.0);

This one shows the <span> with the stars. What I am doing wrong in the first function? Thanks in advance.

Maramal
  • 3,145
  • 9
  • 46
  • 90
  • Did you mean to use `return getRating(5.0, $ret);` to return the result? – Dave Jul 29 '19 at 12:55
  • `return $ret . getRating( $rating );` sounds like it would work. – MonkeyZeus Jul 29 '19 at 12:55
  • @Dave, look at the first line of the function, `if ($rating == 0) { return $ret; }` – Maramal Jul 29 '19 at 13:00
  • I saw that but it isn't related to what you are asking. – Dave Jul 29 '19 at 13:02
  • Why would you implement this as a recursive function in the first place? The rating stars you want to output don’t require the HTML code to be nested in any way, they are simply elements occurring in straight succession - so _why_ go recursive? – misorude Jul 29 '19 at 13:06
  • @misorude, I think like you say, because of that succession it needs to be recursive. – Maramal Jul 29 '19 at 13:09
  • No, because of that it does _not_ need to be recursive. You want to output X number of elements one after the other here, that can be done using a simple loop, and doesn’t require recursion at any point. – misorude Jul 29 '19 at 13:13
  • Meh, I guess I learned that wrong.. If it works with a loop but less lines of code it can be a recursive function. – Maramal Jul 29 '19 at 13:15

3 Answers3

2

You need to have a return value in your function, and you should call it primarily from the outside. Here is a working example: https://3v4l.org/t2G7F

Code:

function getRating($rating, $ret = '') {
    if ($rating == 0) { return $ret; }
    if ($rating < 1) {
        $ret .= '<span class="fa fa-star-half-empty"></span>';
        $rating-= 0.5;
    } else {
        $ret .= '<span class="fa fa-star"></span>';
        $rating-= 1;
    }
    return getRating($rating, $ret);
}

echo getRating(5.0);
Andrew
  • 827
  • 2
  • 6
  • 14
  • It works, but the second argument is not needed. It only needs the `return` statement. – Maramal Jul 29 '19 at 13:05
  • True, since $ret has a default value among the function parameters. It's just a habbit of mine. Edited answer to remove it and fix a typo. – Andrew Jul 29 '19 at 13:06
1

You can try this by using pass by reference

 function recGerRating(&$rating, &$html=null){
    if($rating == 0 ) return $html;
    if($rating < 1){
      $html .='<span class="fa fa-star-half-empty"></span>';
      $rating-= 0.5;
      return $html;
    }else{
      $html .= '<span class="fa fa-star"></span>';
      $rating-= 1;
      return recGerRating($rating, $html);
    }
  }
 $r = 5;
 echo recGerRating($r);

Live example : https://3v4l.org/k8RXt

Rakesh Jakhar
  • 6,380
  • 2
  • 11
  • 20
0

You can pass variable by link. Always returning response from function more expensive operation than passing variable by link and change it. This approach uses less memory.

function getRating($rating, &$ret) {
    if ($rating == 0) { return; }
    if ($rating < 1) {
        $ret .= '<span class="fa fa-star-half-empty"></span>';
        $rating-= 0.5;
    } else {
        $ret .= '<span class="fa fa-star"></span>';
        $rating-= 1;
    }
    getRating($rating, $ret);
}

$var = "";
getRating(4.5, $var);
echo $var;
potiev
  • 546
  • 2
  • 11