Javascript
訪問映射中的所有元素
我是新手。我正在嘗試訪問申請人結構中的所有元素。在我的捐贈功能中,如果捐贈者未指定要捐贈的組織,則金額將分配給申請人內的所有組織。我在網上查看過,由於 gas 成本高,迭代映射顯然是個壞主意。那我還能怎樣實現我的目標呢?
pragma solidity ^0.4.2; contract DonationContract { address owner; struct Applicant { address Org; string Name; string OrgType; string Number; string Email; uint256 Wallet; uint256 DonationFunds; bool approved; } constructor() public { owner = msg.sender; facilitators[msg.sender] = true; } mapping (address => Applicant) public applicants; mapping(address => bool) facilitators; modifier Owner() { require(msg.sender == owner); _; } modifier OnlyFacilitator() { require(facilitators[msg.sender] == true); _; } modifier Approved(address Org) { require(applicants[Org].approved == true); _; } function approve(address Org) OnlyFacilitator public { applicants[Org].approved = true; } function Donate(uint256 amount, address Org) Approved(Org) public { if(Org==0) { //Split donation amount amongst all applicants donationfunds } else applicants[Org].DonationFunds += amount; if(applicants[Org].DonationFunds >= 10000) { applicants[Org].DonationFunds -=10000; applicants[Org].Wallet += 10000; } } function addFacilitator(address _addr) Owner public { facilitators[_addr] = true; } }
除非您將每個值的鍵儲存在某處,否則您無法遍歷映射。
以下是您可以執行此操作的兩種方法。兩者都有自己的問題。
- (首選/去中心化方式)創建一個功能,允許組織
claim
在契約中進行捐贈。這可以通過一個簡單的 Web 界面讓他們使用變得更容易。該功能將簡單地檢查使用者是否在合約中儲存了資金,並允許他們提取適當的金額。以下是一個我沒有測試過的例子,但應該給你適當的指導。注意:如果組織是自由添加/刪除的,這不起作用,而是存在已知數量的組織並且這不會改變。這只是一般指南,必鬚根據您嘗試實現的特定邏輯進行修改。應該有檢查/要求/等。我沒有包括在內。uint256 public numOfOrgs; // Number of orgs able to claim uint256 public claimIndex; // Count of claimable donations mapping(uint256 => uint256) public claimAmount // The claimable amount per index mapping(address => mapping(uint256 => bool)) public isIndexClaimed; // Amount of ETH each org can claim per claimable event function donate() { // Donation logic where donator does not specify if donatorDidNotSpecify { addIndex(donationAmount) } } function addIndex(uint256 _donationAmount) internal { uint256 amountPerOrg = _donationAmount.div(numOfOrgs); claimAmount[claimIndex] = amountPerOrg; claimIndex += 1; } function claim(uint256 _claimIndex) public { if (isIndexClaimed[msg.sender][_claimIndex] == false) { isIndexClaimed[msg.sender][_claimIndex] = true; // Org cannot claim multiple times per index uint256 amount = claimAmount[_claimIndex]; msg.sender.transfer(amount); } }
- 將地址數據庫(映射的密鑰)保存在鏈下,並執行一個腳本,在捐贈者未指定接收者的情況下將捐贈的內容分發給每個組織。正如您所提到的,隨著更多組織的加入,這將花費您一定數量的 gas。