mirror of
https://github.com/wren-lang/wren.git
synced 2026-01-12 22:58:40 +01:00
267 lines
15 KiB
HTML
267 lines
15 KiB
HTML
<!DOCTYPE html>
|
|
<html>
|
|
<head>
|
|
<meta http-equiv="Content-type" content="text/html;charset=UTF-8" />
|
|
<title>Functions – Wren</title>
|
|
<link rel="stylesheet" type="text/css" href="style.css" />
|
|
<link href='//fonts.googleapis.com/css?family=Source+Sans+Pro:400,700,400italic,700italic|Source+Code+Pro:400|Lato:400|Sanchez:400italic,400' rel='stylesheet' type='text/css'>
|
|
<!-- Tell mobile browsers we're optimized for them and they don't need to crop
|
|
the viewport. -->
|
|
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1"/>
|
|
</head>
|
|
<body id="top">
|
|
<header>
|
|
<div class="page">
|
|
<div class="main-column">
|
|
<h1><a href="./">wren</a></h1>
|
|
<h2>a classy little scripting language</h2>
|
|
</div>
|
|
</div>
|
|
</header>
|
|
<div class="page">
|
|
<nav class="big">
|
|
<ul>
|
|
<li><a href="getting-started.html">Getting Started</a></li>
|
|
<li><a href="contributing.html">Contributing</a></li>
|
|
</ul>
|
|
<section>
|
|
<h2>language guide</h2>
|
|
<ul>
|
|
<li><a href="syntax.html">Syntax</a></li>
|
|
<li><a href="values.html">Values</a></li>
|
|
<li><a href="lists.html">Lists</a></li>
|
|
<li><a href="maps.html">Maps</a></li>
|
|
<li><a href="method-calls.html">Method Calls</a></li>
|
|
<li><a href="control-flow.html">Control Flow</a></li>
|
|
<li><a href="variables.html">Variables</a></li>
|
|
<li><a href="functions.html">Functions</a></li>
|
|
<li><a href="classes.html">Classes</a></li>
|
|
<li><a href="concurrency.html">Concurrency</a></li>
|
|
<li><a href="error-handling.html">Error Handling</a></li>
|
|
<li><a href="modularity.html">Modularity</a></li>
|
|
</ul>
|
|
</section>
|
|
<section>
|
|
<h2>reference</h2>
|
|
<ul>
|
|
<li><a href="modules">Modules</a></li>
|
|
<li><a href="embedding">Embedding</a></li>
|
|
<li><a href="performance.html">Performance</a></li>
|
|
<li><a href="qa.html">Q & A</a></li>
|
|
</ul>
|
|
</section>
|
|
</nav>
|
|
<nav class="small">
|
|
<table>
|
|
<tr>
|
|
<td><a href="getting-started.html">Getting Started</a></td>
|
|
<td><a href="contributing.html">Contributing</a></td>
|
|
</tr>
|
|
<tr>
|
|
<td colspan="2"><h2>language guide</h2></td>
|
|
<td><h2>reference</h2></td>
|
|
</tr>
|
|
<tr>
|
|
<td>
|
|
<ul>
|
|
<li><a href="syntax.html">Syntax</a></li>
|
|
<li><a href="values.html">Values</a></li>
|
|
<li><a href="lists.html">Lists</a></li>
|
|
<li><a href="maps.html">Maps</a></li>
|
|
<li><a href="method-calls.html">Method Calls</a></li>
|
|
<li><a href="control-flow.html">Control Flow</a></li>
|
|
</ul>
|
|
</td>
|
|
<td>
|
|
<ul>
|
|
<li><a href="variables.html">Variables</a></li>
|
|
<li><a href="functions.html">Functions</a></li>
|
|
<li><a href="classes.html">Classes</a></li>
|
|
<li><a href="concurrency.html">Concurrency</a></li>
|
|
<li><a href="error-handling.html">Error Handling</a></li>
|
|
<li><a href="modularity.html">Modularity</a></li>
|
|
</ul>
|
|
</td>
|
|
<td>
|
|
<ul>
|
|
<li><a href="modules">Modules</a></li>
|
|
<li><a href="embedding">Embedding</a></li>
|
|
<li><a href="performance.html">Performance</a></li>
|
|
<li><a href="qa.html">Q & A</a></li>
|
|
</ul>
|
|
</td>
|
|
</tr>
|
|
</table>
|
|
</nav>
|
|
<main>
|
|
<h1>Functions</h1>
|
|
<p>No self-respecting language today can get by without functions—first
|
|
class little bundles of code. Since Wren is object-oriented, most of your code
|
|
will live in methods on classes, but free-floating functions are still
|
|
eminently handy. </p>
|
|
<p>Functions are objects like everything else in Wren, instances of the <code>Fn</code>
|
|
class. </p>
|
|
<h2>Block arguments <a href="#block-arguments" name="block-arguments" class="header-anchor">#</a></h2>
|
|
<p>Most of the time you create a function just to pass it to some method. For
|
|
example, if you want to filter a <a href="lists.html">list</a> by some criteria, you’ll
|
|
call its <code>where</code> method, passing in a function that defines the predicate
|
|
you’re filtering on. </p>
|
|
<p>Since that’s the most common usage pattern, Wren’s syntax optimizes for that.
|
|
Taking a page from Ruby, a function is created by passing a <em>block argument</em> to
|
|
a method. At its simplest, it looks like this: </p>
|
|
<div class="codehilite"><pre><span></span><span class="n">blondie</span><span class="o">.</span><span class="n">callMe</span> <span class="p">{</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="s">"This is the body!"</span><span class="p">)</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>Here we’re invoking the <code>callMe</code> method on <code>blondie</code>. We’re passing one
|
|
argument, a function whose body is the
|
|
following <a href="syntax.html#blocks">block</a>—everything between that pair of
|
|
curly braces. </p>
|
|
<p>Methods that take a block argument receive it as a normal parameter. <code>callMe</code>
|
|
could be defined like so: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">class</span> <span class="vg">Blondie</span> <span class="p">{</span>
|
|
<span class="n">callMe</span><span class="p">(</span><span class="n">fn</span><span class="p">)</span> <span class="p">{</span>
|
|
<span class="c1">// Call it...</span>
|
|
<span class="p">}</span>
|
|
<span class="p">}</span>
|
|
|
|
<span class="k">var</span> <span class="n">blondie</span> <span class="o">=</span> <span class="vg">Blondie</span><span class="o">.</span><span class="n">new</span><span class="p">()</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>A method can take other arguments in addition to the block. They appear before
|
|
the block just like a regular argument list. For example: </p>
|
|
<div class="codehilite"><pre><span></span><span class="n">blondie</span><span class="o">.</span><span class="n">callMeAt</span><span class="p">(</span><span class="mi">867</span><span class="p">,</span> <span class="mi">5309</span><span class="p">)</span> <span class="p">{</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="s">"This is the body!"</span><span class="p">)</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>Of course, you don’t <em>have</em> to use a block argument to pass a function to a
|
|
method. If you already have a function object, you can pass it like a regular
|
|
argument: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">var</span> <span class="n">someFn</span> <span class="o">=</span> <span class="c1">// Get a function...</span>
|
|
<span class="n">blondie</span><span class="o">.</span><span class="n">callMe</span><span class="p">(</span><span class="n">someFn</span><span class="p">)</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>Block arguments are purely sugar for creating a function and passing it in one
|
|
little blob of syntax. There are some times when you want to create a function
|
|
but <em>don’t</em> need to pass it to a method. For that, you can call the <code>Fn</code>
|
|
class’s constructor: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">var</span> <span class="n">someFn</span> <span class="o">=</span> <span class="vg">Fn</span><span class="o">.</span><span class="n">new</span> <span class="p">{</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="s">"Hi!"</span><span class="p">)</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>As you can see it takes a block argument too! All the constructor does it
|
|
return that, so this exists purely as a convenience method for you. </p>
|
|
<h2>Calling functions <a href="#calling-functions" name="calling-functions" class="header-anchor">#</a></h2>
|
|
<p>Once you have a function, how do you invoke it? Like everything in Wren, you do
|
|
so by calling a method on it: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">class</span> <span class="vg">Blondie</span> <span class="p">{</span>
|
|
<span class="n">callMe</span><span class="p">(</span><span class="n">fn</span><span class="p">)</span> <span class="p">{</span>
|
|
<span class="n">fn</span><span class="o">.</span><span class="n">call</span><span class="p">()</span>
|
|
<span class="p">}</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>Functions expose a <code>call()</code> method that executes the body of the function. This
|
|
method is dynamically-dispatched like any other, so you can define your own
|
|
“function-like” classes and pass them to methods that expect “real” functions. </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">class</span> <span class="vg">FakeFn</span> <span class="p">{</span>
|
|
<span class="n">call</span><span class="p">()</span> <span class="p">{</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="s">"I'm feeling functional!"</span><span class="p">)</span>
|
|
<span class="p">}</span>
|
|
<span class="p">}</span>
|
|
|
|
<span class="n">blondie</span><span class="o">.</span><span class="n">callMe</span><span class="p">(</span><span class="vg">FakeFn</span><span class="o">.</span><span class="n">new</span><span class="p">())</span>
|
|
</pre></div>
|
|
|
|
|
|
<h2>Function parameters <a href="#function-parameters" name="function-parameters" class="header-anchor">#</a></h2>
|
|
<p>Of course, functions aren’t very useful if you can’t pass values to them. The
|
|
functions that we’ve seen so far take no arguments. To change that, you can
|
|
provide a parameter list surrounded by <code>|</code> immediately after the opening brace
|
|
of the body, like so: </p>
|
|
<div class="codehilite"><pre><span></span><span class="n">blondie</span><span class="o">.</span><span class="n">callMe</span> <span class="p">{</span><span class="o">|</span><span class="n">first</span><span class="p">,</span> <span class="n">last</span><span class="o">|</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="s">"Hi, "</span> <span class="o">+</span> <span class="n">first</span> <span class="o">+</span> <span class="s">" "</span> <span class="o">+</span> <span class="n">last</span> <span class="o">+</span> <span class="s">"!"</span><span class="p">)</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>Here we’re passing a function to <code>greet</code> that takes two parameters, <code>first</code> and
|
|
<code>last</code>. They are passed to the function when it’s called: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">class</span> <span class="vg">Blondie</span> <span class="p">{</span>
|
|
<span class="n">callMe</span><span class="p">(</span><span class="n">fn</span><span class="p">)</span> <span class="p">{</span>
|
|
<span class="n">fn</span><span class="o">.</span><span class="n">call</span><span class="p">(</span><span class="s">"Debbie"</span><span class="p">,</span> <span class="s">"Harry"</span><span class="p">)</span>
|
|
<span class="p">}</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>It’s an error to call a function with fewer arguments than its parameter list
|
|
expects. If you pass too <em>many</em> arguments, the extras are ignored. </p>
|
|
<h2>Returning values <a href="#returning-values" name="returning-values" class="header-anchor">#</a></h2>
|
|
<p>The body of a function is a <a href="syntax.html#blocks">block</a>. If it is a single
|
|
expression—more precisely if there is no newline after the <code>{</code> or
|
|
parameter list—then the function implicitly returns the value of the
|
|
expression. </p>
|
|
<p>Otherwise, the body returns <code>null</code> by default. You can explicitly return a
|
|
value using a <code>return</code> statement. In other words, these two functions do the
|
|
same thing: </p>
|
|
<div class="codehilite"><pre><span></span><span class="vg">Fn</span><span class="o">.</span><span class="n">new</span> <span class="p">{</span> <span class="s">"return value"</span> <span class="p">}</span>
|
|
|
|
<span class="vg">Fn</span><span class="o">.</span><span class="n">new</span> <span class="p">{</span>
|
|
<span class="k">return</span> <span class="s">"return value"</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<h2>Closures <a href="#closures" name="closures" class="header-anchor">#</a></h2>
|
|
<p>As you expect, functions are closures—they can access variables defined
|
|
outside of their scope. They will hold onto closed-over variables even after
|
|
leaving the scope where the function is defined: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">class</span> <span class="vg">Counter</span> <span class="p">{</span>
|
|
<span class="k">static</span> <span class="n">create</span><span class="p">()</span> <span class="p">{</span>
|
|
<span class="k">var</span> <span class="err">i</span> <span class="o">=</span> <span class="mi">0</span>
|
|
<span class="k">return</span> <span class="vg">Fn</span><span class="o">.</span><span class="n">new</span> <span class="p">{</span> <span class="err">i</span> <span class="o">=</span> <span class="err">i</span> <span class="o">+</span> <span class="mi">1</span> <span class="p">}</span>
|
|
<span class="p">}</span>
|
|
<span class="p">}</span>
|
|
</pre></div>
|
|
|
|
|
|
<p>Here, the <code>create</code> method returns the function created on its second line. That
|
|
function references a variable <code>i</code> declared outside of the function. Even after
|
|
the function is returned from <code>create</code>, it is still able to read and assign
|
|
to<code>i</code>: </p>
|
|
<div class="codehilite"><pre><span></span><span class="k">var</span> <span class="n">counter</span> <span class="o">=</span> <span class="vg">Counter</span><span class="o">.</span><span class="n">create</span><span class="p">()</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="n">counter</span><span class="o">.</span><span class="n">call</span><span class="p">())</span> <span class="output">1</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="n">counter</span><span class="o">.</span><span class="n">call</span><span class="p">())</span> <span class="output">2</span>
|
|
<span class="vg">System</span><span class="o">.</span><span class="n">print</span><span class="p">(</span><span class="n">counter</span><span class="o">.</span><span class="n">call</span><span class="p">())</span> <span class="output">3</span>
|
|
</pre></div>
|
|
|
|
|
|
<p><a class="right" href="classes.html">Classes →</a>
|
|
<a href="variables.html">← Variables</a> </p>
|
|
</main>
|
|
</div>
|
|
<footer>
|
|
<div class="page">
|
|
<div class="main-column">
|
|
<p>Wren lives
|
|
<a href="https://github.com/munificent/wren">on GitHub</a>
|
|
— Made with ❤ by
|
|
<a href="http://journal.stuffwithstuff.com/">Bob Nystrom</a> and
|
|
<a href="https://github.com/munificent/wren/blob/master/AUTHORS">friends</a>.
|
|
</p>
|
|
<div class="main-column">
|
|
</div>
|
|
</footer>
|
|
</body>
|
|
</html>
|