Solidity 变量的数据位置规则

1. 规则1 – 状态变量

状态变量总是存储在存储区中。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract DataLocation {  
   // storage     
   uint stateVariable;  
   uint[] stateArray;  
}  

此外,不能显式地标记状态变量的位置。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract DataLocation {  
   uint storage stateVariable; // 错误  
   uint[] memory stateArray; // 错误  
} 

2. 规则2 – 函数参数与返回值

函数参数包括返回参数都存储在内存中。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract DataLocation {  
   // storage     
   uint stateVariable;  
   uint[] stateArray;  

   function calculate(uint num1, uint num2) public pure returns (uint result) {
       return num1 + num2;
   }
} 

此处,函数参数 uint num1 与 uint num2,返回值 uint result 都存储在内存中。

3. 规则3 – 局部变量

值类型的局部变量存储在内存中。但是,对于引用类型的局部变量,需要显式地指定数据位置。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract Locations {  
  /* 此处都是状态变量 */  
  // 存储在storage中  
  bool flag;  
  uint number;  
  address account;  

  function doSomething() public pure  {  
    /* 此处都是局部变量  */  
    // 值类型
    // 所以它们被存储在内存中
    bool flag2;  
    uint number2;  
    address account2;  

    // 引用类型,需要显示指定数据位置,此处指定为内存
    uint[] memory localArray;        
  }  
}   

不能显式覆盖具有值类型的局部变量。

  
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
function doSomething() public  {  
    /* 此处都是局部变量  */  
    // 值类型
    bool memory flag2;  // 错误
    uint Storage number2;  // 错误 
    address account2;  
  }   

4. 规则4 – 外部函数的参数

外部函数的参数(不包括返回参数)存储在 calldata中。

下一章:Solidity 赋值的数据位置规则

solidity 数据可以通过两种方式从一个变量复制到另一个变量。一种方法是复制整个数据(按值复制),另一种方法是引用复制。solidity 从一个位置的变量赋值到另一个位置的变量,遵循一定的默认规则。 ...