solidity icon indicating copy to clipboard operation
solidity copied to clipboard

Optional function parameters

Open VoR0220 opened this issue 8 years ago • 45 comments

Not too dissimilar to Python, but basically parameters that default to a certain value should they not be filled. Would make for flexibility in contracts.

VoR0220 avatar Nov 19 '15 14:11 VoR0220

I fear this rather has to be not too dissimilar to C++, as we have to generate a fixed signature for every function.

chriseth avatar Nov 19 '15 16:11 chriseth

I'm not sure I'm understanding the fears here. Can you elaborate as to what this would mean in the grand scheme of the VM/Gas/etc?

VoR0220 avatar Nov 19 '15 16:11 VoR0220

Ok, I probably did not use the right words. I think this is a good feature, and it will be more similar to how it is in C++ than how it is in Python. There will be distinct functions (as far as the ABI is concerned) for each number of given arguments. It might be difficult to implement that for external functions because we cannot write to CALLDATA.

chriseth avatar Nov 23 '15 15:11 chriseth

okay. Cool. :)

VoR0220 avatar Nov 23 '15 16:11 VoR0220

@VoR0220 do you think we should close this in favour of #240 which has more details?

axic avatar Aug 02 '16 20:08 axic

I dont think so personally.

VoR0220 avatar Aug 03 '16 14:08 VoR0220

Well...maybe. Idk. Definitely would need to change the title of the old issue i think.

VoR0220 avatar Aug 03 '16 14:08 VoR0220

Yes, the title should be changed.

axic avatar Aug 03 '16 17:08 axic

Definitely in favor of including optional parameters with optional defaults in the language. Especially useful as an alternative to constructor overloading.

joejordan avatar Dec 27 '17 20:12 joejordan

+1

anaibol avatar Jan 24 '18 13:01 anaibol

+1

Dan195 avatar May 06 '18 16:05 Dan195

+1

alexroan avatar Jun 10 '18 08:06 alexroan

+1

iluxa avatar Jun 21 '18 13:06 iluxa

+1

dariodjurica avatar Jun 22 '18 10:06 dariodjurica

+1

FaranLogicon avatar Jul 04 '18 08:07 FaranLogicon

+1

nei-oliveiraneto avatar Jul 09 '18 14:07 nei-oliveiraneto

+1

karthiknvlr avatar Jul 11 '18 08:07 karthiknvlr

I understand that default parameter can be easier to use, but it's unnecessary:

contract Donations {
    event Donated(uint256 value, address donator, string name);
    
    function donate(string _name) public payable {
        emit Donated(msg.value, msg.sender, _name);
    }
    
    function donate() public payable {
        donate("Anonymous");
    }
}

Let's keep Solidity simple.

MichalZalecki avatar Jul 15 '18 10:07 MichalZalecki

+1

I believe @MichalZalecki 's solution works as long as there's only one optional parameter

hdahme avatar Jul 23 '18 21:07 hdahme

+1

vutsalsinghal avatar Aug 04 '18 19:08 vutsalsinghal

Could this work like C++ does? As far as I am aware, C++ generates one function and just adds the missing ones to a call when a caller doesn't include all arguments.

randomnetcat avatar Aug 04 '18 20:08 randomnetcat

Added to 0.5.1.

chriseth avatar Aug 06 '18 13:08 chriseth

С++-inspired solution makes it impossible to implement things like:

function myFunc(uint i = 1)
function myFunc(string s = "")

... which is, probably, force better code design.

zaytsevand avatar Sep 07 '18 19:09 zaytsevand

@chriseth does your comment mean it's now available? If so, what would the syntax be? or where could I find the documentation?

abunsen avatar Jan 12 '19 21:01 abunsen

No, it is not implemented yet. We used "0.5.1" as a codeword for "after 0.5.0", which grew too large after some time and was renamed to "backlog non-breaking".

chriseth avatar Jan 14 '19 11:01 chriseth

Whats the status on this piece?

onigiri-x avatar Feb 15 '19 18:02 onigiri-x

Status is "Neither fully specified nor planned".

chriseth avatar Feb 18 '19 13:02 chriseth

Just to make it explicit: do the mentions of C++ mean variadic/vararg-style functions? Seeing that the abi.encode() functions are variadic made me think that the functionality HAD to be supported, so maybe mentioning that it is not would be helpful.

hmijail avatar Jul 17 '19 02:07 hmijail

Variadic functions are a different category, so they are out of scope for this issue. I also think that it is much easier to get something wrong than it is already with default arguments.

chriseth avatar Jul 17 '19 06:07 chriseth

I agree that it is easier to get something wrong, and yet lack of variadic functions forces boilerplate and code repetition, which also causes its own problems.

hmijail avatar Jul 18 '19 03:07 hmijail

This issue has been stale for quite some time, but I feel like the discussion should be kept relevant. Answeing to what @MichalZalecki said Although what he suggested works, it does not work for constructors. If I'd like to have optional parameters in the constructor, I'd have to duplicate my constructur, one with the parameters and one without them, and would get an error while compiling saying that I already have a constructor defined elasewhere.

litvinjuan avatar Jan 03 '20 14:01 litvinjuan

Changing the way the constructor works would be a breaking change beyond the compiler/language, but every web3 tool would need to be changed. The reason is the "function signature" is not transmitted for constructor parameters, so there's no way to tell them apart.

Under what circumstances is it important to have different constructors? Why not just create different contracts, inheriting from the same, with different constructors:

contract A {
  constructor(uint a) public { }
}

contract DefaultA is A {
  constructor() A(1) public { }
}

axic avatar Jan 03 '20 15:01 axic

@axic One scenario would be where you have a really flexible agreement. For example you might have a weekly agreement and a monthly agreement. It'd be handy from a dApp point of view to only have to deploy and manage one type of smart contract, then be able to initialise it by just calling different constructors instead of having to deploy a specific type of agreement and manage multiple ones on the app side.

You could absolutely do what you're suggesting and just deploy different contracts for the various types of agreements, it's just really heavy in some cases if the differences are small. Most programming languages I know of support this type of polymorphic constructor, so it's a useful pattern to have available, but there is absolutely a workaround that works as you say.

thekevinbrown avatar Aug 07 '20 07:08 thekevinbrown

С++-inspired solution makes it impossible to implement things like:

function myFunc(uint i = 1)
function myFunc(string s = "")

... which is, probably, force better code design.

Same as c#, Java, Python etc.

bitcoinbrisbane avatar Oct 14 '20 00:10 bitcoinbrisbane

Any update on this feature?

aress31 avatar Apr 28 '21 23:04 aress31

How about now?

s3hMC avatar May 22 '21 13:05 s3hMC

That status is still the same as in https://github.com/ethereum/solidity/issues/232#issuecomment-464729858:

Status is "Neither fully specified nor planned".

axic avatar May 22 '21 13:05 axic

That status is still the same as in #232 (comment):

Status is "Neither fully specified nor planned".

That's unfortunate.

s3hMC avatar May 22 '21 20:05 s3hMC

i'm working with a constructor that accepts either an existing address if an external contract is known, or it deploys a new contract based on config for that contract if needed

doing this 2-3 times shows why the "why don't you just use inheritance" argument is limited, and function overloading too, because it ends up needing every combination of present/not-present arguments specified

if you have 3 arguments that are optional you need to specify 2^3 contracts/overloads, and so on...

thedavidmeister avatar Jun 04 '21 09:06 thedavidmeister

Another use case is testing functions when running dapptools. It would be nice to have functions used for some tests to have optional parameters

AlbertSu123 avatar Nov 23 '21 08:11 AlbertSu123

alternatively, an Option or Maybe type would work fine by lifting the issue up to the struct level as optional field values would be equivalently expressive

thedavidmeister avatar Jan 11 '22 13:01 thedavidmeister

There's an ongoing discussion related to default parameters on the forum: Reducing Calldata Size with Optional/Default Function Parameters. Anyone wants to chime in?

cameel avatar Jan 11 '22 17:01 cameel

Any update to optional params yet?

dbaileydev avatar Jul 09 '22 21:07 dbaileydev

@thedavidmeister yes Maybe Monad at struct level would be good to have if Union types are supported.


// syntax could be like
// define Union
Union Optional<address>  { Nothing, Something<address> }

// declare union variable
Optional<address> owner;

// assign union variable
owner = Something(0x0000000000000000000000000000000000001010)

5hanth avatar Jul 27 '22 00:07 5hanth

personally i've mostly moved away from using structs like this because the support for it is pretty bad

thedavidmeister avatar Jul 29 '22 10:07 thedavidmeister