contract ChallengeManager is Owned {
Challenge[] public challenges;
struct Participant {
address participantAddress;
bool participate;
uint goal;
}
struct Challenge {
string name;
uint256 timestamp;
address owner;
bytes32 challengeHash;
Participant[] participants;
}
}
Now, i can't initialized the Participant[] array inside Challenge.
Using this line when initializing struct
new Participant[](0)
i get the following error:
UnimplementedFeatureError: Copying of type struct ChallengeManager.Participant memory[] memory to storage not yet supported.
A less elegant solution i thought is deleting Participant struct and modify Challenge like this:
struct Challenge {
string name;
uint256 timestamp;
address owner;
bytes32 challengeHash;
address[] participantAddress;
bool[] participate;
uint[] goal;
}
But this _is not a great solution_ in my opinion.
We will soon have challenges.pushEmpty() or something like that. Until then, please use challenges.length++; and then initialize using Challenge storage c = challenges[challenges.length - 1]; c.name = ...
Any update on this?
Is there anyway to initialized a Struct which contains an Array of Structs?
Let's suppose we have this contract:
contract ChallengeManager is Owned { Challenge[] public challenges; struct Participant { address participantAddress; bool participate; uint goal; } struct Challenge { string name; uint256 timestamp; address owner; bytes32 challengeHash; Participant[] participants; } }Now, i can't initialized the Participant[] array inside Challenge.
Using this line when initializing structnew Participant[](0)i get the following error:
UnimplementedFeatureError: Copying of type struct ChallengeManager.Participant memory[] memory to storage not yet supported.
A less elegant solution i thought is deleting Participant struct and modify Challenge like this:
struct Challenge { string name; uint256 timestamp; address owner; bytes32 challengeHash; address[] participantAddress; bool[] participate; uint[] goal; }But this _is not a great solution_ in my opinion.
Do you have any suggestion?
There is .push() now.
@chriseth I can see how you can .push() a new Challenge to the challenges array. But how do you initialise an empty participants array on the Challenge struct?
The below is failing with
UnimplementedFeatureError: Copying of type struct ChallengeManager.Participant memory[] memory to storage not yet supported.
contract ChallengeManager {
struct Participant {
address participantAddress;
bool participate;
}
struct Challenge {
bytes32 challengeHash;
uint256 timestamp;
address owner;
Participant[] participants;
}
Challenge[] public challenges;
function addChallenge(bytes32 _challengeHash) public {
challenges.push(Challenge({
challengeHash: _challengeHash,
timestamp: now,
owner: msg.sender,
participants: new Participant[](0)
}));
}
}
I've also tried the below but this fails with This variable is of storage pointer type and can be accessed without prior assignment, which would lead to undefined behaviour.
function addChallenge(bytes32 _challengeHash) public {
Challenge storage newChallange;
newChallange.hash = _challengeHash;
newChallange.timestamp = now;
newChallange.owner = msg.sender;
challenges.push(newChallange);
}
I worked out how to do the above. You can push an empty struct to the storage array and then update the properties you want. Any properties you don't update will have a default value. In the below case, participants on the Challenge struct will be an empty array of Participant structs.
pragma solidity ^0.6.6;
contract ChallengeManager {
struct Participant {
address participantAddress;
bool participate;
}
struct Challenge {
bytes32 hash;
uint256 timestamp;
address owner;
Participant[] participants;
}
Challenge[] public challenges;
function addChallenge(bytes32 _challengeHash) public {
challenges.push();
uint256 newIndex = challenges.length - 1;
challenges[newIndex].hash = _challengeHash;
challenges[newIndex].timestamp = now;
challenges[newIndex].owner = msg.sender;
}
}