This is the class that I have created in PHP
class userinfo
{
public $username;
public $totalscore;
public $userid;
}
The code below is in a finite loop, and i is set to 0 before entering the loop. And the variable user_array is defined to be an array using the following code:
$user_array = array();
(some code here...)
$i++;
$user_array[i] = new userinfo();
$user_array[i]->totalscore = $stattotal;
$user_array[i]->userid = $id;
For some reason I cant understand why this wont work. I need to create an array of objects. And each object must hold three variables. How do I go about doing so ?
Thank you in Adv. for your Help !
Worked fine for me, remember the $ when using variables.
http://phpfiddle.org/main/code/muv-yx6
You must have a dollar sign ($i) before all variables in PHP.
You can use get_class_vars method to get all properties of class
$my_class = new myclass();
$class_vars = get_class_vars(get_class($my_class));
foreach ($class_vars as $name => $value) {
echo "$name : $value\n";
}
SOURCE : http://php.net/manual/en/function.get-class-vars.php
Related
I am trying to convert my string on id's into variable names and inject them into my function.
I have a json object with the following information in it:
Object
(
[files] => file1.php,fie2.php
[dependencies] => db,templates
[classname] => SomeClass
)
I am able to loop through everything and get it to work with a single variable name, but when there is more than one dependency, I need to loop through them, make them variables, and then pass to a function depending on how many are needed dynamically from this object above.
// First I make sure the dependency object exists, this one has 'db,templates' in it
if (!empty($json_data->dependencies)) {
// I explode them into an array, to see if there is more than one
$dependence_string = explode(",", $json_data->dependencies);
if (is_array($dependence_string)) {
// I make a dummy variable
$dependencies = NULL;
foreach ($dependence_string as $dependency) {
$dependencies[] = '$' . $dependency;
}
// Now i have an array with two values "$db", "$templates"
// This gets inserted as new SomeClass(Array()); but I need to
// somehow be able to convert it to new SomeClass($db, $templates);
$some_value = new $json_data->classname($dependencies);
} else {
// This is easy to handle and is done already
}
Now i have an array with two values "$db", "$templates" and this gets inserted as new SomeClass(Array()); but I need to somehow be able to convert it to new SomeClass($db, $templates); and keep them comma separated as variables from their string names.
What method would I use for this? I tried implode but it still sends as a string and I need to convert it to individual items and send however many the current script needs to run.
Got it to work with the following code:
foreach ($dependence_string as $dependency) {
$dependencies[] = '$' . $dependency;
}
$some_value = (new ReflectionClass($json_data->classname))->newInstanceArgs($dependencies);
The splat operator could be the solution to your issue.
<?php
declare(strict_types=1);
namespace Marcel;
class SomeClass
{
protected string $db;
protected string $templates;
public function __construct(string $db, string $templates)
{
$this->db = $db;
$this->templates = $templates;
}
}
foreach ($dependence_string as $dependency) {
$dependencies[] = '$' . $dependency;
}
$class = new SomeClass(...$dependencies);
Type hinting is not required but would be nice. To keep the example simple, strings are used here.
I created a class. The code is below
class Another {
public $error = array();
public function set_error( $key, $value )
{
if ( isset( $key ) ) {
$sanitizedKey = sanitize_key( $key );
$this->error[ $sanitizedKey ] = wp_json_encode( $value );
return $this->error;
}
}
public function get_error( $id )
{
if ( ! is_null( $id ) ) {
return $this->error[ $id ];
}
}
public function print_error()
{
if ( $this->error ) {
foreach ($this->error as $key => $value) {
$decodeJson = json_decode( $value );
?>
<div class="ud-error">
<p class="ud-error-<?php echo $key; ?>">
<?php echo __( $decodeJson, 'ud-for-edd' ); ?>
</p>
</div>
<?php
}
}
}
}
If I invoke it in the following way it works. It echos the content as expected.
$error = new Another();
$error->set_error('gg', 'hhhh');
$error->print_error();
But if I use it with function then it doesn't work as expected. Do I have to pass parameters by reference or any other? The following way it doesn't work
function create_error($id, $val) {
$errr = new Another();
return $errr->set_error($id, $val);
}
create_error('raa', 'raashid');
$error = new Another();
$error->print_error();
I am confused about why this doesn't work. Any clue. Thanks in advance.
Steps I want the code to perform:
Create a class with 3 methods, set_error, get_error, and print_error
Then invoke the class inside the function. The function will accept two parameters because inside the class the set_error() method accepts two parameters.
In order to print the error, I will instantiate the class and call the print_error() method.
In case, if I have to print the new error. I will just call the create_error() function to do this for me. Because the function needs 2 parameters. The arguments supplied to the function must be supplied as arguments to the set_error() method.
I hope the list helps.
Update:
If I use a global variable then it works. Below is working.
$customError = new Another();
function create_error($id, $val) {
global $customError;
$customError->set_error($id, $val);
}
create_error('raa', 'rashid');
$customError->print_error();
Thanks, #roggsFolly and #El_Vanja. By understanding your tips I was able to solve the error. If there is anything wrong with the code I just said worked. Please point out.
The object you instantiate inside the function is not the same one you try and print the error message from.
First the object you instantiate inside the function scope is not visible outside the function.
function create_error($id, $val) {
$errr = new Another();
return $errr->set_error($id, $val);
}
create_error('raa', 'raashid');
// this instantiates a seperate Another object from the one
// you created in the function
$error = new Another();
// this tries to print from the new object taht has no message stored in it yet
$error->print_error();
To instantiate the object inside a function scope and then use that object outside the function scope you must pass that object back to the caller of the function
function create_error($id, $val) {
$errr = new Another();
$errr->set_error($id, $val);
return $errr; // this returns the object
}
$error = create_error('raa', 'raashid');
// now you can use its methods to print the stored message
$error->print_error();
Update as per your additional Information
A couple of things I think you may be getting confused about.
Each time you do $var = new ObjectName; you are creating a brand new instance of that class. This new instance has no knowledge about any other instances of that class that may or may not have been created before or may be created after that point. And more specifically to your problems, it does not have access to the properties of another version of that object.
You are I believe missing the concept of variable scope. The Object you create inside that function, will only actually exist while the function is running. Once the function completes anything created/instantiated wholly within that function is DESTROYED ( well in truth it is just no longer accessible ) but to all intent and purpose it is destroyed. you therefore cannot expect to be able to address it outside the scope of the function.
If you want the Object you instantiate within the function to be usable outside the function, you must pass a reference to that object out of the function to the calling code. This passes that reference into the scope of the calling code and keeps the object alive, global scope in your case, but that might be another function or even another object. That allows you access to that instantiation and any properties that were set within it.
I'm refactoring all the codes given to me and I saw in the code that the're so many repeated variables that is using with other methods
which is this
$tag_id = json_decode($_POST['tag_id']);
$tag_name = json_decode($_POST['tag_name']);
$pname = json_decode($_POST['pname']);
$icode = json_decode($_POST['icode']);
$bname = json_decode($_POST['bname']);
$client = json_decode($_POST['client']);
$package = json_decode($_POST['package']);
$reference = json_decode($_POST['reference']);
$prodcat = json_decode($_POST['prodcat']);
$physical_array = json_decode($_POST['physical_array']);
$chemical_array = json_decode($_POST['chemical_array']);
$physpec_array = json_decode($_POST['physpec_array']);
$micro_array = json_decode($_POST['micro_array']);
$microspec_array = json_decode($_POST['microspec_array']);
$prod_type = json_decode($_POST['prod_type']);
$create_physical_id_array = json_decode($_POST['create_physical_id_array']);
$create_chemical_id_array = json_decode($_POST['create_chemical_id_array']);
$create_micro_id_array = json_decode($_POST['create_micro_id_array']);
my question is how can i just use put it in one method and i'll just call it to other methods instead of repeating that code.
thank you
You can't call it from other methods. Because the variables defined to that method are local. Instead you can define the variables as member variables of that class and access from any method or even from outside class depending upon the access specifier.
protected $a=2;
public function method1()
{
echo $this->a;
}
public function method2()
{
echo $this->a;
}
Put it in an array
$post_array = [];
foreach($_POST as $key => $value)
{
$post_array[$key] = json_decode($value);
}
return $post_array;
and then call it like this
$post_array['create_micro_id_array'];
Since it appears you are very much aware of the variable names you want to use... I'll suggest PHP Variable variables
To do this, you can loop through your $_POST and process the value while using the key as variable name.
foreach($_POST as $key => $value)
{
$$key = json_decode($value);
}
At the end of the day, these 4 lines would generate all that... However i'm not so sure of how friendly it may appear to someone else looking at the code. Give it a shot.
You may try extract function.
extract($_POST);
I have the following codes.
<?php
class Reg {
private $pros = array();
public function __set($key,$val) {
$this->pros($key)= $val;
}
public function __get($key) {
return $this->pros($key);
}
}
$reg= new Reg;
$reg->tst="tst";
echo $reg->tst;
?>
But when executing this script I got the error following.
Fatal error : can't use method return value in write context in line 5
I believe that to add an element to array is possible like the above.
$array = array();
$array('key')='value';
Please make clear that I was wrong.
Thanks
The is because of you are trying to set a functions return value. $this->pros($key) means calling pros($key) function. Not setting a value to $pros array.
The syntax is wrong. Setting values to array be -
$array['index'] = 'value';
Change
$this->pros($key)= $val; -> $this->pros[$key]= $val;
and
return $this->pros[$key];
Working code
$this->pros[$key] = $value;
OR
$keys = array($key);
$this->pros = array_fill_keys($keys,$value);
The array_fill_keys() function fills an array with values, specifying keys.
Syntax:
array_fill_keys(keys,value);
This Class gives me a blank output even if I change return to echo, I'm not sure what the issue is but I'm obviously not that versed in dealing with Classes and Objects.
I'm sure I'm just handling the variables/arrays incorrectly, but I can't see where, maybe the variables shouldn't be declared under Class since they should only be returned if a person is created? Should I declare variables in the function, or not declare them at all since they should be handled by $args?
Updated Question: How do I get it to return every argument not just FIRSTNAME?
PHP:
class people_handler
{
public $firstname;
public $middlename;
public $lastname;
public $city;
public $province_state;
/* zip+4 is default for postcode (postal code) */
public $postcode;
public $country;
function create_people($args)
{
$fullname=array($this->firstname,$this->middlename,$this->lastname);
$normname=array($this->firstname,$this->lastname);
$fulladdress=array($this->city,$this->province_state,$this->postcode,$this->country);
if(!$args->middlename&&$args->firstname && $args->lastname && $args->city && $args->province_state && $args->postcode && $args->country)
{
$temp_arr=array($normname,$fulladdress);
foreach($temp_arr as $value)
{
foreach($value as $values)
{
return $values;
}
}
}
else if($args->firstname && $args->middlename && $args->lastname && $args->city && $args->province_state && $args->postcode && $args->country)
{
$temp_arr=array($fullname,$fulladdress);
foreach($temp_arr as $value)
{
foreach($value as $values)
{
return $values;
}
}
}
else
{
die ("Must enter all values excluding middlename.");
}
}
}
$p1=new people_handler;
$p1->firstname="John";
$p1->middlename="Jonah";
$p1->lastname="Jameson";
$p1->city="Lansing";
$p1->province_state="Michigan";
$p1->postcode="48876-4444";
$p1->country="USA";
echo $p1->create_people($p1);
Returns:
John
You're missing the Object self-reference: $this all over the place.
Anytime you refer to a method or property from within the class, you need to refer to $this as the current instantiation of the Object that is doing the process. So, for instance...
$fullname=array($firstname,$middlename,$lastname);
becomes
$fullname=array($this->firstname,$this->middlename,$this->lastname);
Which should work, since you assigned the values to those properties already.
EDIT: Looking at the code further, constantly returning a value through loops won't manage the echoing to the browser. You can either echo $value instead of returning it, or build an array from the values and return that and have the script handle the array to echo to the browser.
EDIT THE SECOND: To get all the values out, you need to collect them as you build them. Another option is to simply output them to the browser as part of the method. Both options work, but collecting them into an array makes it more portable, but also a fair bit more code to maintain. As well, you do not need to pass the object into itself to get the method to work.
echo $p1->create_people($p1);
Should be...
$p1->create_people();
In create_people you'll have...
function create_people()
{
$fullname=array($this->firstname,$this->middlename,$this->lastname);
$normname=array($this->firstname,$this->lastname);
$fulladdress=array($this->city, $this->province_state, $this->postcode, $this->country);
if($args->firstname && $args->lastname && $args->city && $args->province_state && $args->postcode && $args->country)
{ //Don't bother including middlename if it doesn't matter if it is filled or not...
$temp_arr = array($normname, $fulladdress);
foreach($temp_arr as $value)
{
foreach($value as $values)
{
echo $values;
}
}
} else {
die ("Must enter all values excluding middlename.");
}
}
That should work.
Apart from the self-reference problem (btw the $args is also not needed as this should be the self-reference), your loop structure is wrong.
$temp_arr=array($normname,$fulladdress);
foreach($temp_arr as $value)
{
foreach($value as $values)
{
return $values;
}
}
This will:
Loop through temp_arr, finding $normname as the first value
Treat $normname as an array and loop through it
Return the first value it finds in $normname
That concludes the function, everything else is not executed.
A function can only have one return value. If you need to return information on more than one thing, you need to return it as an array or as an object so that it is all wrapped up in one element.
At the moment I'm not quite sure what you're trying to accomplish with your class, so unfortunately I can't help you with what you need to do.
Edit: You don't need to return anything in that case. Your class makes those variables accessible to all functions within the class already. With "new" you create an instance of the object, that is you create "a people_handler". This people_handler has properties about it, which you made public, so they can be set from outside the class (which may not be a great idea in a bigger project but seems fine for this). All functions which are part of the class (that is, inside it), can access what values these properties currently have for that certain people_handler by using the self-reference, $this:
class TestClass {
public fullname; //a random "property"
function echoFullname() {
echo $this->fullname; //whatever fullname is at the moment for the TestClass object we are using
}
}
$a = new TestClass(); //Create a TestClass object
$a->fullname = "Alex"; //make its name "Alex"
$b = new TestClass(); //Create another TestClass object
$b->fullname = "Carl"; //but let's name him Carl
$a->echoFullname(); //And now output the names
$b->echoFullname();
Obviously this has no practical use but hopefully illustrates how it works.As you can see, variable passing wasn't necessary at all.
at line 14:
$fullname=array($firstname,$middlename,$lastname);
Probably should be:
$fullname=array($this->firstname,$this->middlename,$this->lastname);
same one line 16:
$fulladdress=array($city,$province_state,$postcode,$country);