0

I had this code previously in which I was trying to create a struct to store 13 strings and I was getting error CompilerError: Stack too deep, try removing local variables..

Code:

  pragma solidity ^0.4.18;

  contract TEST {

  struct Test {
    string a;
    string b;
    string c;
    string d;
    string e;
    string f;
    string g;
    string h;
    string i;
    string j;
    string k;
    string l;
    string m;
  }

  mapping (uint => Test) test;
  uint totalTests;

  function totalTestsCount() view public returns (uint) {
    return totalTests;
  }

  function createTest(string a, string b, string c, string d, string e, string f, string g, string h, string i, string j, string k, string l, string m) public returns (uint) {

    uint test_id = totalTests++;

    test[test_id] = Test(a, b, c, d, e, f, g, h, i, j, k, l, m);

    return test_id;
  } 

  function showTest(uint test_id) view public returns (string, string, string, string, string, string, string, string, string, string, string, string, string){

    Test t_test;
    t_test = test[test_id];

    return (t_test.a, t_test.b, t_test.c, t_test.d, t_test.e, t_test.f, t_test.g, t_test.h, t_test.i, t_test.j, t_test.k, t_test.l, t_test.m);
  } 

}

Then I tried to store all the strings in just one string with a special character to separate them and would parse them out on the client side. But this gave me the error of Infinite gas requirement in the Remix IDE.

Code:

  pragma solidity ^0.4.20;

  contract TEST {

  string Test;

  mapping (uint => string) public test;
  uint totalTests;

  function totalTestsCount() view public returns (uint) {
    return totalTests;
  }

  function createTest(string test_data) public returns (uint) {

    uint test_id = totalTests++;

    test[test_id] = test_data;

    return test_id;
  } 

  function showTest(uint test_id) view public returns (string){

    string memory t_test = test[test_id];

    return (t_test);
  } 

}

Can please someone tell how to get rid of the errors or suggest a better approach to achieve this ?

1 Answer 1

1

In the first case, the issue is too many strings in functions that are limited to 16 args. Strings count for "2" owing to separate length and content in the encoding, so way over budget. You could solve it by instead storing a 13-element array and making a function to retrieve one at a time by index.

In the second case, this line uint test_id = totalTests++; is incrementing the row index from 0 to 1 then trying to write the data to row 1. Row 1 doesn't exist in the dynamic array which has length 0.

I decided to go with a version of the second case, using push(data) to append to the array, and added a few tweaks for good practice. It works in Remix.

pragma solidity ^0.4.20;

contract Test {

  string[] public tests;

  event LogAppendedData(address sender, string data);

  function totalTestsCount() view public returns (uint) {
    return tests.length;
  }

  function appendData(string test_data) public returns (uint count) {
    emit LogAppendedData(msg.sender, test_data);
    return tests.push(test_data);
  } 

  function showTest(uint row) view public returns (string){
    return tests[row];
  } 

}

Hope it helps.

4
  • I'm having trouble with the toolbar in this browser. Maybe a kind soul will jump in and add {} to format that. Commented Mar 15, 2018 at 6:14
  • 1
    did that for you :)
    – Rajesh
    Commented Mar 15, 2018 at 6:43
  • Thank you but still getting the error of infinite gas requirement. Have a look: imgur.com/a/7PAKS Commented Mar 15, 2018 at 6:58
  • Those are warnings. They indicate that the cost of your function cannot be known in advance because you're using strings which can be of any length. The warnings will disappear if you refactor using bytes32 (fixed-length) or you can silence the warnings by unchecking "gas cost" on the static 'Analysis` page. These warnings don't stop you from using the contract. They warn that there is a maximum string length the dev might not know about. Commented Mar 15, 2018 at 14:53

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.