当您将合约存储在映射中时,实际存储了啥?
Posted
技术标签:
【中文标题】当您将合约存储在映射中时,实际存储了啥?【英文标题】:What is actually stored when you store a contract in a mapping?当您将合约存储在映射中时,实际存储了什么? 【发布时间】:2021-10-29 15:58:18 【问题描述】:如果我有一个叫做 Person 的合同,比如说,它包含一个名字和一个年龄,还有一个叫做 People 的合同,这个合同看起来像
contract People
mapping(string => Person) myPeople;
addPerson(string memory name, uint age)
Person person = new Person(name, age);
myPeople[name] = person;
我想知道在这种情况下,区块链中实际发生了什么。我知道声明 Person person = new Person(name, age)
实际上会将新的 Person 合约部署到区块链上(我会为此付费)。但是当我通过myPeople[name] = person;
将其存储在映射中时,我是仅存储合约地址,还是再次存储其所有数据? (即在已部署合约的存储中,以及在 People 合约的存储中。如果是第二个,听起来只存储地址会便宜很多。我注意到我可以从映射,并且可以调用它的函数而不必实例化它,但也许在幕后从它的地址实例化合约有一些魔法,这使得我可以调用它的函数?
【问题讨论】:
这是一个很好的问题。我首先要说我不确定。但我很有信心猜测您的存储中没有合同数据的副本。只是因为这听起来不是一个好计划。考虑一下它的含义,您可能有两个指向相同数据的假定指针,并且可能不同。无论哪种方式,它仍然可能是这种情况,也许我可以编写一些测试并检查 gas 成本.. 【参考方案1】:People
合约存储中存储的实际值(myPeople
映射的每个项下)是已部署的Person
合约的地址。
Person
合约存储在People
合约中不重复。
我可以从映射中检索 Person,并且可以调用它的函数而无需实例化它
当People
合约与Person
实例交互时,它只使用Person
合约的接口。所以People
合约知道Person
有什么函数,期望的参数是什么,返回值等等。
当您从myPeople
映射分配一个变量时,Solidity 使用 local Person
接口。
所以是的,这就是魔法的来源。 :)
【讨论】:
以上是关于当您将合约存储在映射中时,实际存储了啥?的主要内容,如果未能解决你的问题,请参考以下文章
合约代码无法存储,请检查您的gas限制:以太坊智能合约部署失败: