在 Solidity 中返回任意长度的结构数组
Returning arbitraty length array of structs in Solidity
在合同中,我试图实现某种结构的递归性。
我有一个对应于 Ticket 类型结构的钱包地址映射。
struct Ticket {
uint256 ticketId;
string firstname;
string lastname;
}
mapping (address => Ticket) tickets;
我对这个解决方案的问题是我不知道如何return 每张具有相同地址的票。
function setTicket(address _address, string memory _firstname, string memory _lastname) public returns(uint256){
uint256 ticketNewId = uint256(keccak256(abi.encodePacked(block.timestamp, block.difficulty)));
Ticket storage ticket = tickets[_address];
ticket.firstname = _firstname;
ticket.lastname = _lastname;
ticket.ticketId = ticketNewId;
ticketaccts.push(_address);
return ticketNewId;
}
function getTickets() view public returns(address[] memory){
return ticketaccts;
}
function getTicket(address _address) view public returns (Ticket memory){
return (tickets[_address]);
}
这里是 getTicket() return 给定 _address 的最后一张票。
但我想要的是 return 所有具有相同 _address 的票
我该怎么做?
有一个老式的解决方案可以提供读取调用
一张送多少票getTicketCount(address)
第n张票getTicket(address, n)
最终我选择的解决方案如下:
function getTicketByAddress(address _address) public view returns (Ticket[] memory){
Ticket[] memory ticketByAddress = new Ticket[](tickets[_address].length);
uint numberOfTicket = 0;
for(uint i = 0; i < tickets[_address].length; i++) {
ticketByAddress[numberOfTicket] = tickets[_address][i];
numberOfTicket++;
}
return ticketByAddress; //don't work well in remix!
}
退款功能的用法示例:
function makeRefund(uint256 _ticketId ) public returns(Ticket memory) {
Ticket[] memory ticketByAddress = new Ticket[](tickets[msg.sender].length);
Ticket memory refundTicket;
uint numberOfTicket = 0;
for(uint i = 0; i < tickets[msg.sender].length; i++) {
ticketByAddress[numberOfTicket] = tickets[msg.sender][i];
numberOfTicket++;
}
ticketByAddress[_ticketId].refunded = true;
refundTicket = ticketByAddress[_ticketId];
if(refundTicket.categorie == 1){
uint256 time = (dateEvent - refundTicket.date)/86400;
require(time >= 1, "It is too late for a refund!");
msg.sender.transfer(ticketPrice);
maxTickets++;
totalTicket++;
}
return refundTicket;
}
在合同中,我试图实现某种结构的递归性。
我有一个对应于 Ticket 类型结构的钱包地址映射。
struct Ticket {
uint256 ticketId;
string firstname;
string lastname;
}
mapping (address => Ticket) tickets;
我对这个解决方案的问题是我不知道如何return 每张具有相同地址的票。
function setTicket(address _address, string memory _firstname, string memory _lastname) public returns(uint256){
uint256 ticketNewId = uint256(keccak256(abi.encodePacked(block.timestamp, block.difficulty)));
Ticket storage ticket = tickets[_address];
ticket.firstname = _firstname;
ticket.lastname = _lastname;
ticket.ticketId = ticketNewId;
ticketaccts.push(_address);
return ticketNewId;
}
function getTickets() view public returns(address[] memory){
return ticketaccts;
}
function getTicket(address _address) view public returns (Ticket memory){
return (tickets[_address]);
}
这里是 getTicket() return 给定 _address 的最后一张票。 但我想要的是 return 所有具有相同 _address 的票 我该怎么做?
有一个老式的解决方案可以提供读取调用
一张送多少票
getTicketCount(address)
第n张票
getTicket(address, n)
最终我选择的解决方案如下:
function getTicketByAddress(address _address) public view returns (Ticket[] memory){
Ticket[] memory ticketByAddress = new Ticket[](tickets[_address].length);
uint numberOfTicket = 0;
for(uint i = 0; i < tickets[_address].length; i++) {
ticketByAddress[numberOfTicket] = tickets[_address][i];
numberOfTicket++;
}
return ticketByAddress; //don't work well in remix!
}
退款功能的用法示例:
function makeRefund(uint256 _ticketId ) public returns(Ticket memory) {
Ticket[] memory ticketByAddress = new Ticket[](tickets[msg.sender].length);
Ticket memory refundTicket;
uint numberOfTicket = 0;
for(uint i = 0; i < tickets[msg.sender].length; i++) {
ticketByAddress[numberOfTicket] = tickets[msg.sender][i];
numberOfTicket++;
}
ticketByAddress[_ticketId].refunded = true;
refundTicket = ticketByAddress[_ticketId];
if(refundTicket.categorie == 1){
uint256 time = (dateEvent - refundTicket.date)/86400;
require(time >= 1, "It is too late for a refund!");
msg.sender.transfer(ticketPrice);
maxTickets++;
totalTicket++;
}
return refundTicket;
}