Shoelace formula for polygonal area: Difference between revisions
Shoelace formula for polygonal area (view source)
Revision as of 15:37, 5 February 2024
, 3 months ago→{{header|Wren}}: Changed to Wren S/H
m (→{{header|Wren}}: Changed to Wren S/H) |
|||
(10 intermediate revisions by 7 users not shown) | |||
Line 18:
{{trans|Python}}
<
R abs(sum(zip(x, y[1..] [+] y[0.<1]).map((i, j) -> i * j))
-sum(zip(x[1..] [+] x[0.<1], y).map((i, j) -> i * j))) / 2
Line 26:
V y = points.map(p -> p[1])
print(area_by_shoelace(x, y))</
{{out}}
Line 34:
=={{header|360 Assembly}}==
<
SHOELACE CSECT
USING SHOELACE,R15 base register
Line 59:
PG DC CL12' ' buffer
REGEQU
END SHOELACE</
{{out}}
<pre>
Line 68:
{{libheader|Action! Tool Kit}}
{{libheader|Action! Real Math}}
<
PROC Area(INT ARRAY xs,ys BYTE count REAL POINTER res)
Line 130:
Test(xs,ys,5)
RETURN</
{{out}}
[https://gitlab.com/amarok8bit/action-rosetta-code/-/raw/master/images/Shoelace_formula_for_polygonal_area.png Screenshot from Atari 8-bit computer]
Line 141:
{{works with|Ada|Ada|83}}
<
procedure Shoelace_Formula_For_Polygonal_Area
Line 172:
begin
Ada.Text_IO.Put_Line(Shoelace(my_polygon)'Img);
end Shoelace_Formula_For_Polygonal_Area;</
{{out}}
<pre> 3.00000E+01
Line 228:
=={{header|ALGOL 68}}==
<
# returns the area of the polygon defined by the points p using the Shoelace formula #
OP AREA = ( [,]REAL p )REAL:
Line 257:
print( ( fixed( AREA [,]REAL( ( 3.0, 4.0 ), ( 5.0, 11.0 ), ( 12.0, 8.0 ), ( 9.0, 5.0 ), ( 5.0, 6.0 ) ), -6, 2 ), newline ) )
END
</syntaxhighlight>
{{out}}
<pre>
Line 265:
=={{header|APL}}==
{{works with|Dyalog APL}}
<
{{out}}
<pre> shoelace (3 4) (5 11) (12 8) (9 5) (5 6)
30</pre>
=={{header|Arturo}}==
<syntaxhighlight lang="arturo">define :point [x,y][]
shoelace: function [pts][
[leftSum, rightSum]: 0
loop 0..dec size pts 'i [
j: (i + 1) % size pts
'leftSum + pts\[i]\x * pts\[j]\y
'rightSum + pts\[j]\x * pts\[i]\y
]
return 0.5 * abs leftSum - rightSum
]
points: @[
to :point [3.0, 4.0]
to :point [5.0, 11.0]
to :point [12.0, 8.0]
to :point [9.0, 5.0]
to :point [5.0, 6.0]
]
print shoelace points</syntaxhighlight>
{{out}}
<pre>30.0</pre>
=={{header|AutoHotkey}}==
<
n := V.Count()
for i, O in V
Sum += V[i, 1] * V[i+1, 2] - V[i+1, 1] * V[i, 2]
MsgBox % result := Abs(Sum += V[n, 1] * V[1, 2] - V[1, 1] * V[n, 2]) / 2</
{{out}}
<pre>30.000000</pre>
=={{header|BASIC256}}==
<
dim array = {{3,4}, {5,11}, {12,8}, {9,5}, {5,6}}
Line 296 ⟶ 324:
sum -= p[1][1] * p[i][2]
return abs(sum) \ 2
end function</
=={{header|C}}==
Reads the points from a file whose name is supplied via the command line, prints out usage if invoked incorrectly.
<syntaxhighlight lang="c">
#include<stdlib.h>
#include<stdio.h>
Line 348 ⟶ 376:
return 0;
}
</syntaxhighlight>
Input file, first line specifies number of points followed by the ordered vertices set with one vertex on each line.
<pre>
Line 366 ⟶ 394:
=={{header|C sharp|C#}}==
{{trans|Java}}
<
using System.Collections.Generic;
Line 395 ⟶ 423:
}
}
}</
{{out}}
<pre>Given a polygon with vertices [(3, 4), (5, 11), (12, 8), (9, 5), (5, 6)],
Line 402 ⟶ 430:
=={{header|C++}}==
{{trans|D}}
<
#include <tuple>
#include <vector>
Line 432 ⟶ 460:
auto ans = shoelace(points);
cout << ans << endl;
}</
{{out}}
<pre>30</pre>
=={{header|Cowgol}}==
<
typedef Coord is uint16; # floating point types are not supported
Line 475 ⟶ 503:
var polygon: Point[] := {{3,4},{5,11},{12,8},{9,5},{5,6}};
print_i16(shoelace(&polygon[0], @sizeof polygon));
print_nl();</
{{out}}
<pre>30</pre>
=={{header|D}}==
<
Point[] pnts = [{3,4}, {5,11}, {12,8}, {9,5}, {5,6}];
Line 508 ⟶ 536:
auto ans = shoelace(pnts);
assert(ans == 30);
}</
{{out}}
<pre>30</pre>
=={{header|Delphi}}==
{{works with|Delphi|6.0}}
{{libheader|SysUtils,StdCtrls}}
In keeping with the principles of modularity and reusability, the problem has been broken down into subroutines that can process any polygon. In other words, the subroutines don't just solve the area of one polygon; they can find the area of any polygon.
<syntaxhighlight lang="Delphi">
{Create a 2D vector type}
type T2DVector = record
X, Y: double;
end;
{Test polygon}
var Polygon: array [0..4] of T2DVector =
((X:3; Y:4), (X:5; Y:11), (X:12; Y:8), (X:9; Y:5), (X:5; Y:6));
function GetPolygonArea(Polygon: array of T2DVector): double;
{Return the area of the polygon }
{K = [(x1y2 + x2y3 + x3y4 + ... + xny1) - (x2y1 + x3y2 + x4y3 + ... + x1yn)]/2}
var I,Inx: integer;
var P1,P2: T2DVector;
var Sum1,Sum2: double;
begin
Result:=0;
Sum1:=0; Sum2:=0;
for I:=0 to Length(Polygon)-1 do
begin
{Vector back to the beginning}
if I=(Length(Polygon)-1) then Inx:=0
else Inx:=I+1;
P1:=Polygon[I];
P2:=Polygon[Inx];
Sum1:=Sum1 + P1.X * P2.Y;
Sum2:=Sum2 + P2.X * P1.Y;
end;
Result:=abs((Sum1 - Sum2)/2);
end;
procedure ShowPolygon(Poly: array of T2DVector; Memo: TMemo);
var I: integer;
var S: string;
begin
S:='';
for I:=0 to High(Poly) do
S:=S+Format('(%2.1F, %2.1F) ',[Poly[I].X, Poly[I].Y]);
Memo.Lines.Add(S);
end;
procedure ShowPolygonArea(Memo: TMemo);
var Area: double;
begin
ShowPolygon(Polygon,Memo);
Area:=GetPolygonArea(Polygon);
Memo.Lines.Add('Area: '+FloatToStrF(Area,ffFixed,18,2));
end;
</syntaxhighlight>
{{out}}
<pre>
(3.0, 4.0) (5.0, 11.0) (12.0, 8.0) (9.0, 5.0) (5.0, 6.0)
Area: 30.00
Elapsed Time: 3.356 ms.
</pre>
=={{header|EasyLang}}==
<syntaxhighlight lang="easylang">
proc shoelace . p[][] res .
sum = 0
for i = 1 to len p[][] - 1
sum += p[i][1] * p[i + 1][2]
sum -= p[i + 1][1] * p[i][2]
.
sum += p[i][1] * p[1][2]
sum -= p[1][1] * p[i][2]
res = abs sum / 2
.
data[][] = [ [ 3 4 ] [ 5 11 ] [ 12 8 ] [ 9 5 ] [ 5 6 ] ]
shoelace data[][] res
print res
</syntaxhighlight>
=={{header|Elixir}}==
<syntaxhighlight lang="elixir">
def shoelace(points) do
points
|> Enum.reduce({0, List.last(points)}, fn {x1, y1}, {sum, {x0, y0}} ->
{sum + (y0 * x1 - x0 * y1), {x1, y1}}
end)
|> elem(0)
|> div(2)
end
</syntaxhighlight>
=={{header|F_Sharp|F#}}==
<
// Shoelace formula for area of polygon. Nigel Galloway: April 11th., 2018
let fN(n::g) = abs(List.pairwise(n::g@[n])|>List.fold(fun n ((nα,gα),(nβ,gβ))->n+(nα*gβ)-(gα*nβ)) 0.0)/2.0
printfn "%f" (fN [(3.0,4.0); (5.0,11.0); (12.0,8.0); (9.0,5.0); (5.0,6.0)])</
{{out}}
<pre>
Line 524 ⟶ 650:
=={{header|Factor}}==
By constructing a <code>circular</code> from a sequence, we can index elements beyond the length of the sequence, wrapping around to the beginning. We can also change the beginning of the sequence to an arbitrary index. This allows us to use <code>2map</code> to cleanly obtain a sum.
<
IN: rosetta-code.shoelace
Line 540 ⟶ 666:
[ shoelace-sum ] 2bi@ - abs 2 / ;
input shoelace-area .</
{{out}}
<pre>
Line 550 ⟶ 676:
Except for the use of "END FUNCTION ''name'' instead of just END, and the convenient function SUM with array span expressions (so SUM(P) rather than a DO-loop to sum the elements of array P), both standardised with F90, this would be acceptable to F66, which introduced complex number arithmetic. Otherwise, separate X and Y arrays would be needed, but complex numbers seemed convenient seeing as (x,y) pairs are involved. But because the MODULE facility of F90 has not been used, routines invoking functions must declare the type of the function names, especially if the default types are unsuitable, as here. In function AREA, the x and y parts are dealt with together, but in AREASL they might be better as separate arrays, thus avoiding the DIMAG and DBLE functions to extract the x and y parts. Incidentally, the x and y parts can be interchanged and the calculation still works. Comparing the two resulting areas might give some indication of their accuracy.
If the MODULE protocol were used, the size of an array parameter is passed as a secret additional parameter accessible via the special function UBOUND, but otherwise it must be passed as an explicit parameter. A quirk of the compiler requires that N be declared before it appears in <code>DOUBLE COMPLEX P(N)</code> so as it is my practice to declare parameters in the order specified, here N comes before P. However, it is not clear whether specifying P(N) does much good (as in array index checking) as an alternative is to specify P(*) meaning merely that the array has one dimension, or even P(12345) to the same effect, with no attention to the actual numerical value. See for example [[Array_length#Fortran]] <
C Uses the mid-point rule for integration. Consider the line joining (x1,y1) to (x2,y2)
C The area under that line (down to the x-axis) is the y-span midpoint (y1 + y2)/2 times the width (x2 - x1)
Line 599 ⟶ 725:
A2 = AREASL(5,POINT)
WRITE (6,*) "A=",A1,A2
END</
Output: WRITE (6,*) means write to output unit six (standard output) with free-format (the *). Note the different sign convention.
Line 613 ⟶ 739:
===Fortran I===
In orginal FORTRAN 1957:
<
C SHOELACE FORMULA FOR POLYGONAL AREA
DIMENSION X(33),Y(33)
Line 631 ⟶ 757:
303 FORMAT(F10.2)
</syntaxhighlight>
{{in}}
<pre>
Line 647 ⟶ 773:
=={{header|FreeBASIC}}==
<
' compile with: fbc -s console
Line 679 ⟶ 805:
Print : Print "hit any key to end program"
Sleep
End</
{{out}}
<pre>The area of the polygon = 30</pre>
Line 685 ⟶ 811:
=={{header|Fōrmulæ}}==
{{FormulaeEntry|page=https://formulae.org/?script=examples/Shoelace_formula_for_polygonal_area}}
'''Solution'''
[[File:Fōrmulæ - Shoelace formula 01.png]]
'''Test case'''
[[File:Fōrmulæ - Shoelace formula 02.png]]
[[File:Fōrmulæ - Shoelace formula 03.png]]
=={{header|Go}}==
<
import "fmt"
Line 710 ⟶ 842:
func main() {
fmt.Println(shoelace([]point{{3, 4}, {5, 11}, {12, 8}, {9, 5}, {5, 6}}))
}</
{{out}}
<pre>
Line 717 ⟶ 849:
=={{header|Haskell}}==
<
----------- SHOELACE FORMULA FOR POLYGONAL AREA ----------
Line 737 ⟶ 869:
main =
print $
shoelace [(3, 4), (5, 11), (12, 8), (9, 5), (5, 6)]</
{{out}}
<pre>30.0</pre>
Line 745 ⟶ 877:
Implementation:
<
0.5*|+/((* 1&|.)/ - (* _1&|.)/)|:y
)</
Task example:
<
30</
Exposition:
Line 758 ⟶ 890:
We start with our list of coordinate pairs
<
3 4
5 11
12 8
9 5
5 6</
But the first thing we do is transpose them so that x coordinates and y coordinates are the two items we are working with:
<
3 5 12 9 5
4 11 8 5 6</
We want to rotate the y list by one (in each direction) and multiply the x list items by the corresponding y list items. Something like this, for example:
<
33 40 60 54 20</
Or, rephrased:
<
33 40 60 54 20</
We'll be subtracting what we get when we rotate in the other direction, which looks like this:
<
15 20 _72 _18 _5</
Finally, we add up that list, take the absolute value (there are contexts where signed area is interesting - for example, some graphics application - but that was not a part of this task) and divide that by 2.
Line 791 ⟶ 923:
{{trans|Kotlin}}
{{works with|Java|9}}
<
public class ShoelaceFormula {
Line 829 ⟶ 961:
System.out.printf("its area is %f,%n", area);
}
}</
{{out}}
<pre>Given a polygon with vertices [(3, 4), (5, 11), (12, 8), (9, 5), (5, 6)],
Line 835 ⟶ 967:
=={{header|JavaScript}}==
<
"use strict";
Line 993 ⟶ 1,125:
// MAIN ---
return main();
})();</
{{Out}}
<pre>Polygonal area by shoelace formula:
Line 1,003 ⟶ 1,135:
===={{trans|Wren}}====
<
def shoelace:
. as $a
Line 1,011 ⟶ 1,143:
[ [3, 4], [5, 11], [12, 8], [9, 5], [5, 6] ]
| "The polygon with vertices at \(.) has an area of \(shoelace)."</
{{out}}
<pre>
Line 1,017 ⟶ 1,149:
</pre>
===={{trans|Julia}}====
<
def sumprod: reduce .[] as [$x,$y] (0; . + ($x * $y));
. as {$x, $y}
Line 1,025 ⟶ 1,157:
{x: [3, 5, 12, 9, 5], y: [4, 11, 8, 5, 6] }
| zip_shoelace</
{{out}}
As above.
Line 1,033 ⟶ 1,165:
{{trans|Python}}
<
Assumes x,y points go around the polygon in one direction.
"""
Line 1,041 ⟶ 1,173:
x, y = [3, 5, 12, 9, 5], [4, 11, 8, 5, 6]
@show x y shoelacearea(x, y)</
{{out}}
Line 1,049 ⟶ 1,181:
=={{header|Kotlin}}==
<
class Point(val x: Int, val y: Int) {
Line 1,071 ⟶ 1,203:
println("Given a polygon with vertices at $v,")
println("its area is $area")
}</
{{out}}
Line 1,080 ⟶ 1,212:
=={{header|Lambdatalk}}==
<
{def shoelace
{lambda {:pol}
Line 1,108 ⟶ 1,240:
{shoelace {pol}}
-> 30
</syntaxhighlight>
=={{header|Lua}}==
<
local function det2(i,j)
return ps[i][1]*ps[j][2]-ps[j][1]*ps[i][2]
Line 1,118 ⟶ 1,250:
for i=1,#ps-1 do sum = sum + det2(i,i+1)end
return math.abs(0.5 * sum)
end</
Using an accumulator helper inner function
<
local function ssum(acc, p1, p2, ...)
if not p2 or not p1 then
Line 1,132 ⟶ 1,264:
local p = {{3,4}, {5,11}, {12,8}, {9,5}, {5,6}}
print(shoeArea(p))-- 30 </
both version handle special cases of less than 3 point as 0 area result.
=={{header|Maple}}==
<syntaxhighlight lang="maple">
with(ArrayTools):
Line 1,197 ⟶ 1,329:
P1 := Polygon(Array([Point(3,4), Point(5,11), Point(12,8), Point(9,5), Point(5,6)])):
area(P1);
</syntaxhighlight>
{{out}}<pre>
Line 1,205 ⟶ 1,337:
=={{header|Mathematica}}/{{header|Wolfram Language}}==
Geometry objects built-in in the Wolfram Language
<
{{out}}
<pre>30</pre>
Line 1,211 ⟶ 1,343:
=={{header|min}}==
{{works with|min|0.19.3}}
<
(((first) (rest)) cleave append) :rotate
((0 <) (-1 *) when) :abs
Line 1,231 ⟶ 1,363:
) :shoelace
((3 4) (5 11) (12 8) (9 5) (5 6)) shoelace print</
{{out}}
<pre>
Line 1,238 ⟶ 1,370:
=={{header|MiniScript}}==
<
sum = 0
points = vertices.len
Line 1,258 ⟶ 1,390:
print "The polygon area is " + shoelace(verts)
</syntaxhighlight>
{{out}}
<pre>
Line 1,265 ⟶ 1,397:
=={{header|Modula-2}}==
<
FROM RealStr IMPORT RealToStr;
FROM FormatString IMPORT FormatString;
Line 1,320 ⟶ 1,452:
ReadChar;
END ShoelaceFormula.</
=={{header|Nim}}==
<
Point = tuple
x: float
Line 1,338 ⟶ 1,470:
var points = [(3.0, 4.0), (5.0, 11.0), (12.0, 8.0), (9.0, 5.0), (5.0, 6.0)]
echo shoelace(points)</
{{out}}
Line 1,345 ⟶ 1,477:
=={{header|Perl}}==
<
use warnings;
use feature 'say';
Line 1,363 ⟶ 1,495:
say area_by_shoelace( [ [3,4], [5,11], [12,8], [9,5], [5,6] ] );
say area_by_shoelace( @poly );
say area_by_shoelace( \@poly );</
{{out}}
<pre>30
Line 1,371 ⟶ 1,503:
=={{header|Phix}}==
<!--<
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span>
<span style="color: #008080;">enum</span> <span style="color: #000000;">X</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">Y</span>
Line 1,387 ⟶ 1,519:
<span style="color: #008080;">constant</span> <span style="color: #000000;">test</span> <span style="color: #0000FF;">=</span> <span style="color: #0000FF;">{{</span><span style="color: #000000;">3</span><span style="color: #0000FF;">,</span><span style="color: #000000;">4</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">5</span><span style="color: #0000FF;">,</span><span style="color: #000000;">11</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">12</span><span style="color: #0000FF;">,</span><span style="color: #000000;">8</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">9</span><span style="color: #0000FF;">,</span><span style="color: #000000;">5</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">5</span><span style="color: #0000FF;">,</span><span style="color: #000000;">6</span><span style="color: #0000FF;">}}</span>
<span style="color: #0000FF;">?</span><span style="color: #000000;">shoelace</span><span style="color: #0000FF;">(</span><span style="color: #000000;">test</span><span style="color: #0000FF;">)</span>
<!--</
{{out}}
<pre>
Line 1,393 ⟶ 1,525:
</pre>
An alternative solution, which does not need the X,Y enum, and gives the same output:
<!--<
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">shoelace</span><span style="color: #0000FF;">(</span><span style="color: #004080;">sequence</span> <span style="color: #000000;">s</span><span style="color: #0000FF;">)</span>
Line 1,410 ⟶ 1,542:
<span style="color: #008080;">constant</span> <span style="color: #000000;">test</span> <span style="color: #0000FF;">=</span> <span style="color: #0000FF;">{{</span><span style="color: #000000;">3</span><span style="color: #0000FF;">,</span><span style="color: #000000;">4</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">5</span><span style="color: #0000FF;">,</span><span style="color: #000000;">11</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">12</span><span style="color: #0000FF;">,</span><span style="color: #000000;">8</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">9</span><span style="color: #0000FF;">,</span><span style="color: #000000;">5</span><span style="color: #0000FF;">},{</span><span style="color: #000000;">5</span><span style="color: #0000FF;">,</span><span style="color: #000000;">6</span><span style="color: #0000FF;">}}</span>
<span style="color: #0000FF;">?</span><span style="color: #000000;">shoelace</span><span style="color: #0000FF;">(</span><span style="color: #000000;">test</span><span style="color: #0000FF;">)</span>
<!--</
=={{header|PowerBASIC}}==
{{Trans|Visual Basic}}
<
#DIM ALL
#COMPILER PBCC 6
Line 1,436 ⟶ 1,568:
CON.PRINT STR$(ShoelaceArea(x(), y()))
CON.WAITKEY$
END FUNCTION</
{{out}}
<pre>30</pre>
Line 1,442 ⟶ 1,574:
=={{header|Python}}==
===Python: Explicit===
<
"Assumes x,y points go around the polygon in one direction"
return abs( sum(i * j for i, j in zip(x, y[1:] + y[:1]))
Line 1,452 ⟶ 1,584:
30.0
>>>
</syntaxhighlight>
===Python: numpy===
<
# Even simpler:
# In python we can take an advantage of that x[-1] refers to the last element in an array, same as x[N-1].
Line 1,478 ⟶ 1,610:
# before applying the Shoelace formula.
</syntaxhighlight>
===Python: Defined in terms of reduce and cycle===
{{Trans|Haskell}}
{{Works with|Python|3.7}}
<
from itertools import cycle, islice
Line 1,522 ⟶ 1,654:
if __name__ == '__main__':
main()</
{{Out}}
<pre>Polygonal area by shoelace formula:
Line 1,529 ⟶ 1,661:
===Python: Alternate===
This adopts the ''indexing'' used in the numpy example above, but does not require the numpy library.
<
return abs(sum(x[i-1]*y[i]-x[i]*y[i-1] for i in range(len(x)))) / 2.
Line 1,536 ⟶ 1,668:
>>> area_by_shoelace2(x, y)
30.0
>>> </
=={{header|Racket}}==
<
(struct P (x y))
Line 1,552 ⟶ 1,684:
(module+ main
(area (P 3 4) (P 5 11) (P 12 8) (P 9 5) (P 5 6)))</
{{out}}
Line 1,562 ⟶ 1,694:
{{works with|Rakudo|2017.07}}
<syntaxhighlight lang="raku"
(^@p).map({@p[$_;0] * @p[($_+1)%@p;1] - @p[$_;1] * @p[($_+1)%@p;0]}).sum.abs / 2
}
say area-by-shoelace( [ (3,4), (5,11), (12,8), (9,5), (5,6) ] );</
{{out}}
<pre>30</pre>
Line 1,572 ⟶ 1,704:
===Slice and rotation===
{{works with|Rakudo|2017.07}}
<syntaxhighlight lang="raku"
my @x := @p».[0];
my @y := @p».[1];
Line 1,583 ⟶ 1,715:
say area-by-shoelace( [ (3,4), (5,11), (12,8), (9,5), (5,6) ] );
</syntaxhighlight>
{{out}}
<pre>30</pre>
Line 1,590 ⟶ 1,722:
<!--
===endpoints as exceptions===
<
parse arg pts; $polygon = 'polygon area of ' /*get optional args from the CL.*/
if pts='' then pts= '(3,4),(5,11),(12,8),(9,5),(5,6)' /*Not specified? Use default. */
Line 1,602 ⟶ 1,734:
A=A + x.j * (y.jp - y.jm) /*compute a part of the area. */
end /*j*/
say $polygon # " points: " pts ' is ───► ' abs(A/2) /*stick a fork in it, we're done*/</
{{out|output|text= when using the default input:}}
<pre>
Line 1,610 ⟶ 1,742:
=== wrap-around endpoints ===
<
parse arg $; if $='' then $= "(3,4),(5,11),(12,8),(9,5),(5,6)" /*Use the default?*/
A= 0; @= space($, 0) /*init A; elide blanks from pts.*/
Line 1,618 ⟶ 1,750:
do j=1 for #; jm= j-1; jp= j+1; A= A + x.j*(y.jm - y.jp) /*portion of area*/
end /*j*/ /*stick a fork in it, we're done*/
say 'polygon area of ' # " points: " $ ' is ───► ' abs(A/2)</
{{out|output|text= when using the default input:}}
<pre>
Line 1,626 ⟶ 1,758:
===somewhat simplified===
reformatted and suitable for ooRexx. (x.0 etc. not needed)
<syntaxhighlight lang="text">/*REXX program uses a Shoelace formula to calculate the area of an N-sided polygon. */
parse arg pts /*obtain optional arguments from the CL*/
if pts='' then pts= '(3,4),(5,11),(12,8),(9,5),(5,6)' /*Not specified? Use default. */
Line 1,642 ⟶ 1,774:
end
A=abs(A/2) /*obtain half of the ¦ A ¦ sum*/
say 'polygon area of' n 'points:' pts 'is --->' A</
{{out}}
<pre>polygon area of 5 points: (3,4),(5,11),(12,8),(9,5),(5,6) is ---> 30</pre>
Line 1,648 ⟶ 1,780:
===even simpler===
Using the published algorithm
<syntaxhighlight lang="text">/*REXX program uses a Shoelace formula to calculate the area of an N-sided polygon. */
parse arg pts /*obtain optional arguments from the CL*/
if pts='' then pts= '(3,4),(5,11),(12,8),(9,5),(5,6)' /*Not specified? Use default. */
Line 1,662 ⟶ 1,794:
a=a+x.n*y.1-x.1*y.n
a=abs(a)/2
say 'polygon area of' n 'points:' pts 'is --->' a</
{{out}}
<pre>polygon area of 5 points: (3,4),(5,11),(12,8),(9,5),(5,6) is ---> 30</pre>
=={{header|Ring}}==
<
# Project : Shoelace formula for polygonal area
Line 1,682 ⟶ 1,814:
sum = sum - p[1][1] * p[i][2]
return fabs(sum) / 2
</syntaxhighlight>
Output:
<pre>
The area of the polygon = 30
</pre>
=={{header|RPL}}==
{| class="wikitable"
! RPL code
! Comment
|-
|
≪
DUP 1 GET +
0 2 3 PICK SIZE '''FOR''' j
OVER j GET LAST 1 - GET
OVER RE OVER IM * SWAP RE ROT IM * - +
'''NEXT'''
ABS 2 / SWAP DROP
≫ <span style="color:blue">''''SHOEL''''</span> STO
|
<span style="color:blue">'''SHOEL'''</span> ''( { (vertices) } → area ) ''
append 1st vertice at the end
sum = 0 ; loop
get 2 vertices
sum += determinant
end loop
finalize calculation, clean stack
return area
|}
{(3,4) (5,11) (12,8) (9,5) (5,6)} <span style="color:blue">'''SHOEL'''</span>
{{out}}
<pre>
1: 30
</pre>
=={{header|Ruby}}==
<
Point = Struct.new(:x,:y) do
Line 1,712 ⟶ 1,874:
puts Polygon.new([3,4], [5,11], [12,8], [9,5], [5,6]).area # => 30.0
</syntaxhighlight>
=={{header|Scala}}==
<
case class Polygon( pp:List[Point] ) {
Line 1,742 ⟶ 1,904:
println( "Area of " + p + " = " + p.area )
}
</syntaxhighlight>
{{out}}
<pre>Area of Polygon( (3,4), (5,11), (12,8), (9,5), (5,6) ) = 30.0</pre>
Line 1,748 ⟶ 1,910:
=={{header|Sidef}}==
{{trans|Raku}}
<
var x = p.map{_[0]}
var y = p.map{_[1]}
Line 1,760 ⟶ 1,922:
}
say area_by_shoelace([3,4], [5,11], [12,8], [9,5], [5,6])</
{{out}}
<pre>
Line 1,770 ⟶ 1,932:
{{trans|Scala}}
<
struct Point {
Line 1,812 ⟶ 1,974:
])
print("\(poly) area = \(poly.area)")</
{{out}}
Line 1,820 ⟶ 1,982:
=={{header|TI-83 BASIC}}==
{{works with|TI-83 BASIC|TI-84Plus 2.55MP}}
<
Dim([A])->N:0->A
For(I,1,N)
Line 1,826 ⟶ 1,988:
A+[A](I,1)*[A](J,2)-[A](J,1)*[A](I,2)->A
End
Abs(A)/2->A</
{{out}}
<pre>
Line 1,833 ⟶ 1,995:
=={{header|VBA}}==
{{trans|Phix}}<
Public Enum axes
u = 1
Line 1,857 ⟶ 2,019:
Next i
Debug.Print shoelace(tcol)
End Sub</
<pre>30</pre>
=={{header|VBScript}}==
<
Dim points, x(),y()
points = Array(3,4, 5,11, 12,8, 9,5, 5,6)
Line 1,878 ⟶ 2,040:
Next 'i
area = Abs(area)/2
msgbox area,,"Shoelace formula" </
{{out}}
<pre>
Line 1,890 ⟶ 2,052:
{{works with|VBA|6.5}}
{{works with|VBA|7.1}}
<
Public Function ShoelaceArea(x() As Double, y() As Double) As Double
Line 1,917 ⟶ 2,079:
Next i
Debug.Print ShoelaceArea(x(), y())
End Sub</
{{out}}
<pre>30</pre>
Line 1,923 ⟶ 2,085:
=={{header|Visual Basic .NET}}==
{{trans|C#}}
<
Imports Point = System.Tuple(Of Double, Double)
Line 1,951 ⟶ 2,113:
End Sub
End Module</
{{out}}
<pre>Given a polygon with vertices [(3, 4), (5, 11), (12, 8), (9, 5), (5, 6)],
Line 1,957 ⟶ 2,119:
=={{header|Wren}}==
<
var area = 0
for (i in 0...pts.count-1) {
Line 1,966 ⟶ 2,128:
var pts = [ [3, 4], [5, 11], [12, 8], [9, 5], [5, 6] ]
System.print("The polygon with vertices at %(pts) has an area of %(shoelace.call(pts)).")</
{{out}}
Line 1,974 ⟶ 2,136:
=={{header|XPL0}}==
<
int N, X, Y;
int S, I;
Line 1,984 ⟶ 2,146:
];
RlOut(0, Shoelace(5, [3, 5, 12, 9, 5], [4, 11, 8, 5, 6]))</
{{out}}
Line 1,993 ⟶ 2,155:
=={{header|zkl}}==
By the "book":
<
xs,ys:=Utils.Helpers.listUnzip(points); // (x,x,...), (y,y,,,)
( xs.zipWith('*,ys[1,*]).sum(0) + xs[-1]*ys[0] -
xs[1,*].zipWith('*,ys).sum(0) - xs[0]*ys[-1] )
.abs().toFloat()/2;
}</
or an iterative solution:
<
xs,ys:=Utils.Helpers.listUnzip(points); // (x,x,...), (y,y,,,)
N:=points.len();
N.reduce('wrap(s,n){ s + xs[n]*ys[(n+1)%N] - xs[(n+1)%N]*ys[n] },0)
.abs().toFloat()/2;
}</
<
areaByShoelace(points).println();
areaByShoelace2(points).println();</
{{out}}
<pre>
|