Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about programming within the scope defined in the help center.
Closed 9 years ago.
Improve this question
I have a function and it works. Please check below:
public static function checkAccessLevel($user, $level) {
public static function checkLevel($user, $level) {
if ($level == "1") {
if (!$user->usertype == 1) {
return array(
'error' => 'Please login before', 'errortype' => 0
);
}
} else if ($level == "2") {
if (!$user->usertype == 2) {
return array(
'error' => 'Please login before', 'errortype' => 0
);
}
} else if ($level == "1,2") {
if (!$user->usertype == 1 || !$user->usertype == 2) {
return array(
'error' => 'Please login before', 'errortype' => 0
);
}
} else {
return array(
'error' => 'Please login before', 'errortype' => 0
);
}
}
I'm looking the way for code optimization. Is it possible to rewrite this function?
$level is always comma separated, just break it and check:
public static function checkLevel($user, $level)
{
$level = explode(',', $level);
if(!in_array($user->usertype, $level))
return array(
'error' => 'Please login before',
'errortype' => 0
);
}
and better yet, throw an Exception or return a boolean.
public static function checkLevel($user, $level)
{
if (($level == "1" && ! $user->usertype == 1) ||
($level == "2" && ! $user->usertype == 2) ||
($level == "1,2" && ! in_array($user->usertype, array(1, 2))) ||
! in_array($level, array("1", "2", "1,2"))) {
return array(
'error' => 'Please login before', 'errortype' => 0
);
}
}
First of all consider using switch, it should be more readable.
Then you may group your conditions, instead of:
} else if ($level == "1,2") {
if (!$user->usertype == 1 || !$user->usertype == 2) {
group them together:
(($level == "1,2") && (!$user->usertype == 1 || !$user->usertype == 2))
Then you may use temporary variable $result:
$result = array('Please login...
and return it at the end, instead of using return keyword in every step, it should help you in debugging.
Also I suggest to read Martin Fowlers book about refactoring which will give you many good advice.
You could use a switch statement instead of an if statement, like so:
public static function checkLevel($user, $level) {
$result = array();
switch($level) {
case '1':
if( $user->usertype == 1) {
$result = array(
'error' => 'Please login before', 'errortype' => 0
);
}
break;
// More cases for each level.
default:
$result = array(
'error' => 'Please login before', 'errortype' => 0
);
}
return $result;
}
Related
I'm trying to make an helper php-function that's going to return true/false if the user got right access level. The access level is set when the user logs in. The problem is that the function always return false. The function is located in a "class" php-file that's included(with include_once) on the page I want to use it.
I'm kinda new to php, but the if conditions seems to be right.
I have tested to log in as admin and "economy", but it doesn't return true.
I also have tried to echoing the value that is sent as an parameter and even checking that the access level is right(by echoing the value) before the elseif statement.
const AccessLevelUser = 0;
const AccessLevelAdmin = 1;
const AccessLevelManager = 2;
const AccessLevelEconomy = 3;
public static function hasAccessLevel($requiredAccess) {
//file_put_contents('logg.txt', $logg);
if( !isset($_SESSION['accesslevel']) ) {
header("location:index.php?location=login");
exit;
}elseif ( $requiredAccess == AccessLevelAdmin && $_SESSION['accesslevel'] == AccessLevelAdmin ) {
echo "Admin True";
return true;
}elseif( $requiredAccess == AccessLevelEconomy && ($_SESSION['accesslevel'] == 3 || $_SESSION['accesslevel'] == 1) ) {
echo "Economy True";
return true;
}elseif( $requiredAccess == AccessLevelManager && ($_SESSION['accesslevel'] == 2 || $_SESSION['accesslevel'] == 1) ) {
echo "Manager True";
return true;
}elseif( $requiredAccess == AccessLevelUser && ($_SESSION['accesslevel'] == 0 || $_SESSION['accesslevel'] == 1) ) {
echo "User True";
return true;
}else{
echo "FALSE!";
return false;
}
}
I am comparing seven (7) boolean values 1 (true) or 0 (false) of a primary set and five (5) of a secondary set with an addition of 2 n/a choices. If all 12 come back as true, then the $class is set to Reuse. If the primary set is True and Secondary is false then it comes back as Resale. If any of the primary set comes back False, it's set to Repair. This is what I have so far, and don't get back any syntax errors, but the "class" is coming back incorrect.
<?php
$primary = false;
$class = null;
if ($_POST['poweradapter'] == "1"
&& $_POST['mobocpu'] == "1"
&& $_POST['memory'] == "1"
&& $_POST['harddrive'] == "1"
&& $_POST['screen'] == "1"
&& $_POST['battery'] == "1"
&& $_POST['hinge'] == "1")
{
$class = "Reuse";
$primary = true;
}
else
{
$class = "Repair or Recycle";
}
if ($primary
&& in_array($_POST['opticaldrive'], ["1", "2"])
&& in_array($_POST['floppydrive'], ["1", "2"])
&& $_POST['usb'] == "1"
&& $_POST['trackpad'] == "1"
&& $_POST['keyboard'] == "1")
{
/*
* "secondary" is implicit here, but we never did anything with the
* $secondary variable in the original script
*/
$class = "Reuse";
}
else
{
$class = ($primary) ? "Reuse" : "Repair or Recycle";
}
?>
Final working script
<?php
$primary = false;
$class = null;
if ($_POST['poweradapter'] == "1"
&& $_POST['mobocpu'] == "1"
&& $_POST['memory'] == "1"
&& $_POST['harddrive'] == "1"
&& $_POST['screen'] == "1"
&& $_POST['battery'] == "1"
&& $_POST['hinge'] == "1")
{
$primary = true;
$class = "Resale";
}
else
{
$class = "Repair or Recycle";
}
if ($primary && in_array($_POST['opticaldrive'], ["1", "2"])
&& in_array($_POST['floppydrive'], ["1", "2"])
&& $_POST['usb'] == "1"
&& $_POST['trackpad'] == "1"
&& $_POST['keyboard'] == "1")
{
$class = "Reuse";
}
?>
The main problem is that you're using double equals in the body of the first if statement.
$class == "Reuse";
$primary == "True";
should be
$class = "Reuse";
$primary = "True";
There are a lot of things you could do to make this more readable and maintainable, but the bug is the equality vs assignment issue.
Here is what I would do to make this easier to work with:
<?php
$primary = false;
$class = null;
if ($_POST['poweradapter'] == "1"
&& $_POST['mobocpu'] == "1"
&& $_POST['memory'] == "1"
&& $_POST['harddrive'] == "1"
&& $_POST['screen'] == "1"
&& $_POST['battery'] == "1"
&& $_POST['hinge'] == "1")
{
$class = "Reuse";
$primary = true;
}
else
{
$class = "Repair or Recycle";
}
if ($primary
&& in_array($_POST['opticaldrive'], ["1", "2"])
&& in_array($_POST['floppydrive'], ["1", "2"])
&& $_POST['usb'] == "1"
&& $_POST['trackpad'] == "1"
&& $_POST['keyboard'] == "1")
{
/*
* "secondary" is implicit here, but we never did anything with the
* $secondary variable in the original script
*/
$class = "Reuse";
}
else
{
$class = ($primary) ? "Resale" : "Repair or Recycle";
}
Hope this helps.
[Edit]
Since you're still having trouble with the logic itself, this is an ideal case for unit testing. Here's a little script you can run from the command line to test and fine tune your logic without having to worry about getting PHPUnit set up:
<?php
class MyService
{
public static $CLASS_REUSE = 'Reuse';
public static $CLASS_RESALE = 'Resale';
public static $CLASS_REPAIR_RECYCLE = 'Repair or Recycle';
public static function determineClassForInputParameters($params)
{
$primary = false;
$class = null;
if ($params['poweradapter'] == "1"
&& $params['mobocpu'] == "1"
&& $params['memory'] == "1"
&& $params['harddrive'] == "1"
&& $params['screen'] == "1"
&& $params['battery'] == "1"
&& $params['hinge'] == "1")
{
$primary = true;
}
if ($primary
&& in_array($params['opticaldrive'], ["1", "2"])
&& in_array($params['floppydrive'], ["1", "2"])
&& $params['usb'] == "1"
&& $params['trackpad'] == "1"
&& $params['keyboard'] == "1")
{
$class = self::$CLASS_REUSE;
}
else
{
$class = ($primary) ? self::$CLASS_RESALE : self::$CLASS_REPAIR_RECYCLE;
}
return $class;
}
}
class MyServiceTest
{
public function __construct()
{
assert_options(ASSERT_ACTIVE, 1);
assert_options(ASSERT_WARNING, 0);
assert_options(ASSERT_QUIET_EVAL, 1);
assert_options(ASSERT_CALLBACK, array($this, 'assertHandler'));
}
public function determineClassForInputParametersShouldReturnReuse()
{
$params = [
'poweradapter' => 1,
'mobocpu' => 1,
'memory' => 1,
'harddrive' => 1,
'screen' => 1,
'battery' => 1,
'hinge' => 1,
'opticaldrive' => 1,
'floppydrive' => 1,
'usb' => 1,
'trackpad' => 1,
'keyboard' => 1
];
$class = MyService::determineClassForInputParameters($params);
if (assert($class == MyService::$CLASS_REUSE, 'Expected class ' . MyService::$CLASS_REUSE . ', found ' . $class))
{
echo "determineClassForInputParametersShouldReturnReuse Passed\n";
}
}
public function determineClassForInputParametersShouldReturnResale()
{
$params = [
'poweradapter' => 1,
'mobocpu' => 1,
'memory' => 1,
'harddrive' => 1,
'screen' => 1,
'battery' => 1,
'hinge' => 1,
'opticaldrive' => 1,
'floppydrive' => 1,
'usb' => 1,
'trackpad' => 1,
'keyboard' => 0
];
$class = MyService::determineClassForInputParameters($params);
if (assert($class == MyService::$CLASS_RESALE, 'Expected class ' . MyService::$CLASS_RESALE . ', found ' . $class))
{
echo "determineClassForInputParametersShouldReturnResale Passed\n";
}
}
public function determineClassForInputParametersShouldReturnRePairOrRecycle()
{
$params = [
'poweradapter' => 0,
'mobocpu' => 1,
'memory' => 1,
'harddrive' => 1,
'screen' => 1,
'battery' => 1,
'hinge' => 1,
'opticaldrive' => 1,
'floppydrive' => 1,
'usb' => 1,
'trackpad' => 1,
'keyboard' => 1
];
$class = MyService::determineClassForInputParameters($params);
if (assert($class == MyService::$CLASS_REPAIR_RECYCLE, 'Expected class ' . MyService::$CLASS_REPAIR_RECYCLE . ', found ' . $class))
{
echo "determineClassForInputParametersShouldReturnRePairOrRecycle Passed\n";
}
}
public function assertHandler($file, $line, $code, $desc = null)
{
echo "Assertion failed at $file:$line: $code";
if ($desc)
{
echo ": $desc";
}
echo "\n";
}
}
$tester = new MyServiceTest();
$tester->determineClassForInputParametersShouldReturnReuse();
$tester->determineClassForInputParametersShouldReturnResale();
$tester->determineClassForInputParametersShouldReturnRePairOrRecycle();
You may find it useful to adopt some of the techniques shown in the test, like encapsulating your logic in a service class to make it easier to test and use in multiple places, using static variables for your "class" names to prevent typo errors, etc. Or you can just tune your logic with this and copy it into your existing code.
It may seem like a lot of overhead, but the few minutes it takes to set up tests for your logic far outweighs the hours you can waste trying to figure it out by submitting requests through your front end.
Here try to first set primary and secondary flag to true or false, then compare for the conditions, below is the code snippet, hope this helps.
There are two problems
1. in the first if you are setting $primary as $primary == "True" instead of $primary="True" , so here instead of setting the primary flag, it is comparing whether $primary is true. same is the case with $class.
in the second if statement -$_POST['floppydrive']=="1" or"2" is always true , so it results in true block of if getting executed every time, here or "2", can be changed to - ($_POST['floppydrive']=="1" || $_POST['floppydrive']=="2")
This should get you desired result
<?php
//setting primary flag
if ($_POST['poweradapter']=="1" && $_POST['mobocpu']=="1" && $_POST['memory']=="1" && $_POST['harddrive']=="1" && $_POST['screen']=="1" && $_POST['battery']=="1" && $_POST['hinge']=="1"){
$primary = "True";
}else{
$primary = "False";
}
//setting secondary flag
if (($_POST['opticaldrive']=="1" || $_POST['opticaldrive']== "2") && ($_POST['floppydrive']=="1" || $_POST['floppydrive']== "2") && $_POST['usb']=="1" && $_POST['trackpad']=="1" && $_POST['keyboard']=="1"){
$secondary = "True";
}else{
$primary = "False";
}
//setting the class now
if ($primary == "True" && $secondary=="True") {
$class = "Reuse";
}
elseif ($primary == "True" && $secondary=="False") {
$class = "Resale";
}
else{
$class = "Repair or Recycle";
}
?>
output
Power Adapter: 1
Motherboard: 1
Memory: 1
Hard/SSD Drive: 1
Screen: 1
Battery: 0
Screen Hinge: 0
USB Ports: 0
Track/Touch Pad: 0
Keyboard: 0
Optical Drive: 0
Floppy Drive: 1
was added with an Class of Repair or Recycle
when I do this in CgridView:
'value' => '$data->status == 1 ? "Payed" : "None" ',
it works, but when I do this:
'value' => 'if ($data->status == 1) { echo "Payed"; } else if($data->status == 2) { echo "Two"; } else { echo "None"; } '.
What I need to do to make work the second statement, or how I need to rewrite it?
Convert your statement to use ternary if:
'value' => '$data->status == 1 ? "Payed": ($data->status == 2 ? "Two" : "None")',
You could also use a function instead to give a bit more flexibility and make it more readable:
'value' => function($row, $data ) {
if ($data->status == 1) { return "Payed"; }
else if($data->status == 2) { return "Two"; }
else { return "None"; }
}
Just in case :
I've tried topher's solution and I found out that I had to switch param like that :
'value' => function($data, $row ) {
if ($data->status == 1) { return "Payed"; }
else if($data->status == 2) { return "Two"; }
else { return "None"; }
}
With topher's solution $data->attribute_name did not work and was, in fact, the row instead of the model..
Perhaps, if you don't need $row, don't pass it.
my solution:
function checkStatus($status)
{
if ($status == 1) {
return "opl";
} else if ($status == 2) {
return "nal";
} else {
return "neopl";
}
}
'value' => 'checkStatus($data->status)',
But your will work too) I will accept answer)
I'm currently writing up a function in order to validate a URL by exploding it into different parts and matching those parts with strings I've defined. This is the function I'm using so far:
function validTnet($tnet_url) {
$tnet_2 = "defined2";
$tnet_3 = "defined3";
$tnet_5 = "defined5";
$tnet_7 = "";
if($exp_url[2] == $tnet_2) {
#show true, proceed to next validation
if($exp_url[3] == $tnet_3) {
#true, and next
if($exp_url[5] == $tnet_5) {
#true, and last
if($exp_url[7] == $tnet_7) {
#true, valid
}
}
}
} else {
echo "failed on tnet_2";
}
}
For some reason I'm unable to think of the way to code (or search for the proper term) of how to break out of the if statements that are nested.
What I would like to do check each part of the URL, starting with $tnet_2, and if it fails one of the checks ($tnet_2, $tnet_3, $tnet_5 or $tnet_7), output that it fails, and break out of the if statement. Is there an easy way to accomplish this using some of the code I have already?
Combine all the if conditions
if(
$exp_url[2] == $tnet_2 &&
$exp_url[3] == $tnet_3 &&
$exp_url[5] == $tnet_5 &&
$exp_url[7] == $tnet_7
) {
//true, valid
} else {
echo "failed on tnet_2";
}
$is_valid = true;
foreach (array(2, 3, 5, 7) as $i) {
if ($exp_url[$i] !== ${'tnet_'.$i}) {
$is_valid = false;
break;
}
}
You could do $tnet[$i] if you define those values in an array:
$tnet = array(
2 => "defined2",
3 => "defined3",
5 => "defined5",
7 => ""
);
Ok, i tested what follows and i'll just let you know what i discovered:
echo ('-1' < 0) ? 'true' : 'false'; // will echo "true"
echo ('1' > 0) ? 'true' : 'false'; // will echo "true"
# Notice that '-1' and '1' are strings
Now let's take an array, coming from the database after filtering all the result in order to get only rows with UID = 1.
$this->a = array(
[0] => array(
'UID' => '1',
'PID' => '91',
'Amount' => '-1'
),
[1] => array(
'UID' => '1',
'PID' => '92',
'Amount' => '1'
),
[2] => array(
'UID' => '1',
'PID' => '93',
'Amount' => '1'
)
);
Now i want to create a function posAmount($PID) that returns true if 'Amount' > 0 or false if 'Amount' < 0. (Notice: Amount = 0 is something i don't really care). Also i'd like to write as similar function called negAmount($PID) that returns the exactely opposite of the first. I'd like, now, to introduce you to my twin functions:
public function posAmount($pid)
{
foreach ($this->a as $a)
{
if (count($this->a) == 0) { return false; }
return ($a['PID'] == $pid and $a['Amount'] > 0) ? true : false;
}
}
public function negAmount($pid)
{
foreach ($this->a as $a)
{
if (count($this->a) == 0) { return false; }
return ($a['PID'] == $pid and $a['Amount'] < 0) ? true : false;
}
}
The cool fact is that, regarding the first array (which, i checked with var_dump() keeps its nature trough the entire script):
$istance->negAmount(91); // Returns true, as expected
$istance->posAmount(92); // Returns false, as NOT expected.
# Why do God wants me to get mad?
The problem is that you are always returning on the first iteration of the foreach loop. You should rewrite the functions like this:
public function negAmount($pid) {
if (count($this->a) == 0) { return false; }
foreach ($this->a as $a) {
if ($a['PID'] == $pid) {
if ($a['Amount'] < 0) {
return true;
}
}
}
return false;
}
public function posAmount($pid) {
if (count($this->a) == 0) { return false; }
foreach ($this->a as $a) {
if ($a['PID'] == $pid) {
if ($a['Amount'] > 0) {
return true;
}
}
}
return false;
}
May just be a typo in your demo code, but posAmount method is looping $this->a, whereas the other is looping $this->votes - OP corrected
You've got some odd things in your code. Why are you checking the count of $this->a from within a foreach loop? It would make more sense to check the count before you start looping.
Also, you've got some logic errors in your comparison. You're only comparing the first iteration through the loop... it will either return true or false for the first index of the array and never even look at the others. You'll want to match the PID in the loop before you compare - and return - any thing. Like so:
public function posAmount($pid)
{
if (count($this->a) == 0) { return false; }
foreach ($this->votes as $a) {
if ($a['PID'] == $pid)
return $a['Amount'] > 0 ? true : false;
}
return false;
}
public function posAmount($pid)
{
if (count($this->a) == 0) { return false; }
foreach ($this->votes as $a) {
if ($a['PID'] == $pid)
return $a['Amount'] < 0 ? true : false;
}
return false;
}
The problem is you're trying to compare a string to an int without trying to convert it. Change $a['Amount'] to (int)$a['Amount'] and see what happens.
So here you iterate $this->a:
public function posAmount($pid)
{
foreach ($this->a as $a)
But here $this->votes:
public function posAmount($pid)
{
foreach ($this->a as $a)
Typo or what...