Suppose I have the defined a struct in solidity as below:
struct Organisation {
string name;
address ethAddress;
uint rating;
string regNumber;
}
I have defined an dynamic array of the above struct as
// list of all insurers/Organisations
Organisation[] allOrgs;
If i need to pass the element of this array to a internal function which is actually just comparing the value against another value, will it be passed by reference?
function getInsurerEth(string uname) public payable returns(address) {
for(uint i = 0; i < allOrgs.length; ++ i) {
if(stringsEqual(allOrgs[i].name, uname)) {
return allOrgs[i].ethAddress;
}
}
}
The function StringsEqual
defined as below. I need to know if the first parameter is passed by reference or value. If by value, then I can actually remove the argument attribute storage
and make the function pure. Also note that this is a internal function call which will use the jump opcode and also i am not editing the storage element allOrgs[i].name
.
// internal function to compare strings
function stringsEqual(string storage _a, string memory _b) internal returns (bool) {
bytes storage a = bytes(_a);
bytes memory b = bytes(_b);
if (a.length != b.length)
return false;
// @todo unroll this loop
for (uint i = 0; i < a.length; i ++)
{
if (a[i] != b[i])
return false;
}
return true;
}
Best Answer
The first argument of function
StringsEqual
is passed by reference and not by value because you are explicitly specifying state variable _a in storage.To declare function
StringsEqual
as pure you need to pass an argument by value as following -To conclude: when you are explicitly defining storage type of an argument as
storage
you are passing an argument to a function by reference.If you don't specify storage type of a function argument then function arguments are always in memory and you are passing an argument to a function by value.
To add further clarification I tried following :
And I get the following error which confirms that argument is passed by reference :