Wanted to share what I learned to help someone in the future running into a similar issue:

I have this struct, which includes two arrays. In createNewEvent, I initialize two arrays, confirmedRSVPs and claimedRSVPS, in memory. In createNewRSVP, I add addresses to this array to keep track of people who have RSVP'd.

My question: Should I be using storage since between function calls, memory is reset between calls and is meant to be temp? I don't want to lose track of who has RSVP'd in past executions of newRSVP, the function that adds addresses to that array.

When I changed the arrays to storage, I got this error: This variable is of storage pointer type and can be accessed without prior assignment, which would lead to undefined behaviour.

struct CreateEvent {
            bytes32 eventId;
            string eventName; 
            address eventOwner;
            uint256 eventTimestamp;
            uint256 deposit;
            uint256 maxCapacity;
            address[] confirmedRSVPs;
            address[] claimedRSVPs;
            bool paidOut;

mapping(bytes32 => CreateEvent) public idToEvent;

    function createNewEvent(
        uint256 eventTimestamp,
        uint256 deposit,
        uint256 maxCapacity,
        string memory eventName
    ) external {
        // generate an eventID based on other things passed in to generate a hash
        bytes32 eventId = keccak256(

        address[] memory confirmedRSVPs; 
        address[] memory claimedRSVPs;

        //this creates a new CreateEvent struct and adds it to the idToEvent mapping
        idToEvent[eventId] = CreateEvent(


function createNewRSVP(bytes32 eventId) external payable {
        // look up event
        CreateEvent storage myEvent = idToEvent[eventId];

        // transfer deposit to our contract / require that they sent in enough ETH
        require(msg.value == myEvent.deposit, "NOT ENOUGH");

        //require that the event hasn't already happened (<eventTimestamp)
        require(block.timestamp <= myEvent.eventTimestamp, "ALREADY HAPPENED");

        //make sure event is under max capacity
            myEvent.confirmedRSVPs.length < myEvent.maxCapacity,
            "This event has reached capacity"

        //require that msg.sender isn't already in myEvent.confirmedRSVPs
        for (uint8 i = 0; i < myEvent.confirmedRSVPs.length; i++) {
            require(myEvent.confirmedRSVPs[i] != msg.sender, "ALREADY CONFIRMED");



Answer: The elements in the array will persist and be stored because they are defined as part of the struct, which is stored in storage. The way the code is written above is the correct way to do this so that the data saved in your array persists despite the array variable being stored in memory because we are saving it to our struct mapping.

Hope this helps others :-)

  • What's the question? What solc version are you testing with?
    – Ismael
    May 11, 2022 at 16:48

1 Answer 1


As your Preference these are two functions. 1) For Add detail using Memory and 2) for Add details for STorage

contract StructArray {
    struct Detail {
        uint256 id;
        string name;
        string[] hobby;

    // in place of this detailing function use mapping that help to use memory in place of structure
    // Detail public detaling;

    // when you need to use mapping no need to use storage you can directly use memory and saving some gas fees
    // This mapping is private beacse when call this method the structure only shows id, name parameter and it ignore array parameter
    mapping(uint256 => Detail) private details;

    // adding details using memory simple way to use memory
    function addDetailMemory(
        uint256 id,
        string memory name,
        string[] memory hobby
    ) external {
        Detail memory d1;

        d1.id = id;
        d1.name = name;
        d1.hobby = hobby;

        details[id] = d1;

    // adding details using storage
    // storage is used when we use for loop and adding single data in a array struct object
    function addDetailStorage(
        uint256 id,
        string memory name,
        string[] memory hobby
    ) external {
        Detail storage d1 = details[id];

        d1.id = id;
        d1.name = name;

        for (uint256 i = 0; i < hobby.length; ) {
            // When you use conditions storage is the good option otherwise we have to use Īḥmemory

            unchecked {

    function viewDetail(uint256 id) external view returns (Detail memory) {
        return details[id];

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.