1

Is there a particular reason why Solidity prevents you from returning structs, lists and other data structures? I understand that it needs to be secure and allowing array/list access may mess with the data, but why not even structs? I'm trying to make a contract which return a list of accidents which have occurred to a particular license plate (which is one of the fields in a struct) from a blockchain of accident records, but I've only managed to get it to return one record, that too by it's individual fields. It just seems very inefficient to me..

Note that I first tried to return string[] but had to change it to bytes[] as Solidity doesn't allow that either.

/*
To get a list of incidents from a startID 
*/
function listIncidents(uint _startID, uint _count) constant returns(uint[10] _incIDs, bytes[10] _names, bytes[10] _descriptions, bytes[10] _places, bytes[10] _times, bytes[10] _dates) {

  uint maxIters = _count;
  if((_startID + _count) > getIncidentCount()) {
  maxIters = getIncidentCount() - _startID;
  }

  _incIDs = new uint[](maxIters);
  _names = new bytes[](maxIters);
  _descriptions = new bytes[](maxIters);
  _places = new bytes[](maxIters);
  _times = new bytes[](maxIters);
  _dates = new bytes[](maxIters);

  for(uint i=0;i<maxIters;i++) {
    uint _incidentID = _startID + i;

    PoliceRecord memory r = incidents[_incidentID];
    _incIDs[i] = _incidentID;
    _names[i] = bytes(r.incName);
    _descriptions[i] = bytes(r.incDescription);
    _places[i] = bytes(r.incPlace);
    _times[i] = bytes(r.incTime);
    _dates[i] = bytes(r.incDate);
   }
}
1

You can return arrays. What you can't do is return arrays of arrays, including string[] or bytes[] (because a string or bytes is already an array).

The reason is just a limitation of the ABI (Application Binary Interface). When you try to do it, you should see a warning from the compiler that says:

This type is only supported in the new experimental ABI encoder. Use "pragma experimental ABIEncoderV2;" to enable the feature.

If you can get away with limiting your strings to length 32, you could use bytes32 instead. This code works fine:

pragma solidity ^0.4.24;

contract Test {
    function test() public pure returns (bytes32[]) {
        bytes32[] memory foo = new bytes32[](2);
        foo[0] = "hello";
        foo[1] = "goodbye";

        return foo;
    }
}
  • Thanks for the answer. I get that strings are an array of arrays, but that's basically a 2D array, and most languages support it, so is there a particular reason why they wouldn't allow returning 2D arrays? Also, how would you get around this problem of returning multiple records in one function call, if say all the fields aren't going to fit in 32 bytes? Thanks. – snazzyslytherin Aug 17 '18 at 13:55
  • As I said, it's just a limitation of the current ABI specification. (It simply doesn't support nested arrays/structs.) It's a design flaw that will presumably be fixed, but I haven't seen a particular ETA. You can turn on the experimental v2 encoder, but just be warned that it's not finalized and so not recommended to use in production yet. – smarx Aug 17 '18 at 14:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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