5 ms·
What makes ME sad is no keyword arguments. Helper/wrapper functions either get an annoying and difficult-to-grok-at-glance associative-array for it's params (ba
by larrik 15y ago
What makes ME sad is no keyword arguments. Helper/wrapper functions either get an annoying and difficult-to-grok-at-glance associative-array for it's params (bad), or a huge list of rarely-used parameters (worse), or a huge set of wrapper functions to set their own paramters (even worse), or outright duplicated functions for similar-but-not-quite tasks (worst).
This happens to me while producing something like a jqGrid, or other javascript/html hybrid stuff that need a few extra options sometimes.
Django/Python? No problem! Just use the keywords you need.
(More Info: The difference between a single associative param standing in for keywords arguments, or a huge list of regular arguments is a choice in complexity/readability IN the function vs. calling it.
For the single dictionary approach, you lost the built-in parameter defaults nicety, which means you need to handle the case of a missing parameter manually. This kind of sucks, especially if you hate seeing PHP Notices during development (which kill JSON/XML output anyway). This makes your function often twice as big (or more) than it needs to be.
For the other approach, you wind up with calling
foo("","","","real value", true, true, 2, false, false, "option I want");*
which just about invites all sorts of hard-to-find bugs, and you have to look at the function definition every time you want to change an option. Also, it's flat-out rude if you aren't the one calling the function.)
- dexen 15y agocompact() + extract() is the closest you get. $foo = 123; $bar = getSomeBar(); myFunction(compact('foo', 'bar')); function myFunction($kwargs) { $foo = SOME_DEFAULT_VALUE; extract($kwargs); if ($foo > 5) { ... } } If you want to `sanitize' which arguments can be passed that way, use extract(array_intersect_key($allowed, $kwargs)); ((EDIT: or use EXTR_IF_EXISTS)). Nb., extract() works on any associative array, you don't have to use compact().
- cag_ii 15y agoWhy would this be any better than just passing in a map of the parameters as the sole parameter? myFunction($parms=array()) { ... } $parms = array('foo' => 'bar', 'baz' => 'yaz'); test($parms);
- dexen 15y agoConcise. Documented, standard and configurable handling of existing variables (may be used for default values etc.) via EXTR_OVERWRITE, EXTR_SKIP, etc. Documented, standard behavior of compact() in regard to missing variables. No manual associating of foo with $foo -- less places for mundane errors. Oh, and there's even that EXTR_IF_EXISTS -- so my silly idea to sanitize with array_intersect_keys() was totally unneeded. Make it $foo = 123; $bar = getSomeBar(); $coot = 'boot'; myFunc(compact('foo', 'bar', 'coot')); function myFunc($kwargs) { $foo = 1; $bar = 'xyz'; extract($kwargs, EXTR_IF_EXISTS); /* sanitization: $coot will NOT get extracted because the function doesn't expect / support that argument */ ... }
- underwater 15y agoIn case you weren't sure on this, it is exactly the same. Compact takes a list of variables names in the local scope and returns an associative array containing their values.
- blake8086 15y agoIsn't a wrapper function the solution to this? Or even... a wrapper function that takes an associative array of options as an argument.
- steve-howard 15y agoYou can use the @ symbol to suppress errors when you're aware that the variable may be empty and you've considered the possible effects. When I used to write PHP, I'd often write something like do_something(@$_GET['foobar']); There are ways to suppress PHP notices without just turning off the E_NOTICE output.
- samdalton 15y agoIt shouldn't be ok to write code that is known to throw an error, and handle it by suppressing that error. Silently failing code is just a bug waiting to happen. It's also making the interpreter do unnecessary error handling work when a simple "if ($_GET['foobar'])" would suffice.
- philjackson 15y agoIt should be ok (the poor PHP implementation aside). Auto-vivification is something that's very useful in Perl and I miss it greatly in the languages I program in now. Being able to do this: $one->{ two }->{ three } = [ $four ] Without having to check every link for definedness makes for cleaner code, IMO. Making it optional "suppressing that error" would be a good middle-ground. Coffeescipt has the existential operator, not quite on a par with Perl's autovivification, which allows: zip = lottery.drawWinner?().address?.zipcode
- samdalton 15y agoThe Coffeescript ? operator is certainly quite handy. I suppose it's explicit nature is what helps, as information on the error you're trying to mask is built into the syntax. With @ in PHP however, you simply don't know what it's trying to stop, and what undesirable affects it may cause, which I think is the main objection to it.
- code_duck 15y agoIt's inefficient to do that, as from what I understand PHP actually sets the error level to none, processes that line, sets it back, and continues. Also it would suppress any other warnings from that line, which could be unrelated to the supplied argument value. Instead, I use a 'get or else' function, as in some functional languages. For arrays, it goes function get_or_else($array,$key,$default=null) { return isset($array[$key]) ? $array[$key] : $default; } This avoids any warnings, and also allows you to specify a default.
- shaunxcode 15y agoHey, in case you are interested I constructed a reply to your post here: http://commonphp.blogspot.com/2011/05/keyword-functions-in-php.html http://commonphp.blogspot.com/2011/05/keyword-functions-in-p... In a nut shell though it's essentially a write up of my library which allows for creating keyword function wrappers so you can do stuff like: myStrPos( needle, 'peter', haystack, 'is peter in here?' );