In this tutorial I'll show how to write a small timeless geometry library for calculating areas.
The purpose of this blog-post is to show the basics of using progsbase. More complex examples will be covered in later posts; for example, check out the Industrial Case: Replacing a Barcode Solution at Inkeria. For a general overview, check out the Progsbase White Paper.
The tool we will use is the progsbase client, progsbase.
First we need to create the standard progsbase folder structure for the project: (The reason for this structure is described elsewhere.)
area/area/main/area/area/
Create a Java source code file area.java
in this folder.
Before we can start to write functions, we need to add the package declaration, import the java.lang.Math
functions and add a class area
.
package area.area;
import static java.lang.Math.*;
public class area{
}
Now, we have a minimal setup, and we are ready to start programming.
A square is a rectangle where all four sides are the same length. If the length of a side is s
,
area = s²
.
We create a function areaOfSquare
that takes the side as a parameter and returns the area. Here is the Java code for the function:
public static double areaOfSquare(double s){
double area;
area = pow(s, 2d);
return area;
}
Both the parameter and the return type is set to double
. progsbase requires arithmetic to have at least 15 decimal digit precision, and the arithmetic must be floating point. double
in Java is compatible with this.
Java supports exponentiation using a function called pow
, short for "power"; we call it to square s
.
Notice that the second parameter, 2d
, is postfixed with a d
. This is because all arithmetic must be floting point, and appending a d
to a number in Java, makes it floating point.
In order to use progsbase, we need a file that describes the program.
In the folder area/area/
, create a file called info.json
.
Write the following in the file:
{
"name": "area",
"version": "0.1.0-SNAPSHOT",
"organization namespace": "no.inductive.idea10.programs",
"scientific namespace": "mathematics.geometry.area",
"imports": [],
"development imports": [],
"ownerCustomerId": "Inductive AS"
}
The name is simply the name of the program, the version is simply the version, and must be formatted as a.b.c
with an optional -SNAPSHOT
at the end, marking the program as an unfinished version and that it will most likely change.
The organization namespace is a namespace that starts with the country code, then continues with the organization name followed by subdivisions within the organization.
The scientific namespace is a namespace that starts with the most general scientific field and then for each part delimits the field until it is specific enough.
The imports
are the other programs this program requires. The development imports
are programs required only for the tests. There are no imports in this example.
The final entry is the ownerCustomerId
. Set this to the customer name you signed up with.
Now, we can compile and analyze the program. In the folder area/area/
run:
progsbase analyze
If this returns without any messages, the program is both valid Java and passes the requirements of progsbase. We can now try the conversion to see what we get for the other languages.
We have already written the library in Java, so C is the second language. In the folder area/area/
run:
progsbase convert Java . "C 99" ../../C
We get the following files:
C/area.h
C/main/area/area/area.c
C/area.h
is the C header files which contains:
#pragma once
#include <stdlib.h>
#include <stdbool.h>
#include <math.h>
#include <string.h>
#define strparam(str) (str), strlen(str)
#ifndef M_PI
#define M_PI 3.14159265358979323846
#endif
double areaOfSquare(double s);
Here we have the required libraries and the declaration of the function. In between are a utility function and a definition of pi.
C/main/area/area/area.c
contains:
#include "area.h"
double areaOfSquare(double s){
double area;
area = pow(s, 2.0);
return area;
}
Here the header file is included first and then the function is defined. This function is quite similar to the Java version except the number is postfixed .0
instead of d
. This is the C-way of saying a number is floating point of type double
.
Let's convert the function to C++. In the folder area/area/
run:
progsbase convert Java . C++ ../../Cpp
We get the following files:
C/area.hpp
C/main/area/area/area.cpp
C/area.hpp
is the C++ header files which contains:
#pragma once
#include <cmath>
#include <cstring>
#include <vector>
using namespace std;
#define toVector(s) (new vector<char> ((s), (s) + strlen(s)))
double areaOfSquare(double s);
The first lines are the required libraries. Then we are using the namespace std
. Then a macro is defined for converting string constants to vector<char>
. Then comes the declaration of the function.
C/main/area/area/area.cpp
contains:
#include "area.hpp"
double areaOfSquare(double s){
double area;
area = pow(s, 2.0);
return area;
}
Which, except for the hpp
-ending of the include, is identical to the C-version.
Lets try converting it to JavaScript. In the folder area/area/
run:
progsbase convert Java . "JavaScript 7" ../../JavaScript7
Now we get the following files:
JavaScript/main/area/area.js
which contains:
function areaOfSquare(s){
var area;
area = s**2;
return area;
}
JavaScript 7 supports exponentiation with the operator **
. JavaScript does not need a suffix on the number 2 as all arithmetic in JavaScript is floating point with at least 15 decimal digits precision. JavaScript 5 is also supported.
Lets convert it to C#. In the folder area/area/
run:
progsbase convert Java . "C#" ../../CS
Now we get the following files:
CS/main/area/area.cs
which contains:
namespace area{
using static System.Math;
public class area{
public static double areaOfSquare(double s){
double area;
area = Pow(s, 2d);
return area;
}
public static void delete(System.Object objectx){
// C# has garbage collection.
}
}
}
Here we first see the namespace declaration followed by an import of System.Math
. Then comes the container class area
. It contains out function areaOfSquare
. The function implementation is very similar to the Java version except the power function has a capital P
.
The delete
function is an empty unallocation function. It is empty in C# because it uses garbage collection. (How this works is desribed in a separate post.)
Lets convert it to php. In the folder area/area/
run:
progsbase convert Java . "PHP 5" ../../PHP
Now we get the following files:
PHP/main/area/area.php
which contains:
<?php
function areaOfSquare($s){
$area = pow($s, 2.0);
return $area;
}
?>
PHP code is sorrounded by the start and end tags <?php and ?>
. Inside, we have the function areaOfSquare
. In php all variables are prefixed with a $
and they are untyped and undeclared.
Lets try converting it to Python. In the folder area/area/
run:
progsbase convert Java . Python ../../Python
Now we get the following files:
Python/main/area/area.py
which contains:
from math import *
def areaOfSquare(s):
area = s**2.0
return area
Python supports exponentiation with the operator **
. As in C, a number must be postfixed with .0
to be floating point. Notice that the variables are not declared and not typed.
The final language is Visual Basic. In the folder area/area/
run:
progsbase convert Java . "Visual Basic 9" ../../VBDotNet
Now we get the following files:
VBDotNet/main/area/area.vb
which contains:
Imports System.Math
Public Module area
Public Function areaOfSquare(s As Double) As Double
Dim area As Double
area = s ^ 2
Return area
End Function
End Module
The first line imports the functions in System.Math
functions. Then comes the container module area
. Inside we have our function areaOfSquare
which is implemented similarly as in JavaScript 7 and Python.
Lets now implement the remaining functions.
The area of a rectangle is:
Area = base * height
This is implemented as:
public static double areaOfRectangle(double b, double h){
double area;
area = b*h;
return area;
}
The area of a triangle is:
Area = 1/2 * base * height
This is implemented as:
public static double areaOfTriangle(double b, double h){
double area;
area = 1d/2d*b*h;
return area;
}
It is interesting to notice that had we omitted the d
-suffices in the formula, the answer would always be 0
. The reason is that then both 1 and 2 would be integers and the division operator would be integer division. 1/2
with integer division is, of course, 0
.
Another formula for the area of a triangle gives the area based on the length of the sides. This is called Heron's formula.
area = √( s(s - a)(s - b)(s - c) )
where
s = (a+b+c)/2
This is implemented as:
public static double areaOfTriangleSides(double a, double b, double c){
double area, s;
s = 1d/2d*(a + b + c);
area = sqrt(s*(s - a)*(s - b)*(s - c));
return area;
}
Notice that the square root operator is supported by the sqrt
function in Java.
The area of a circle is:
Area = π r²
This is implemented as:
public static double areaOfCircle(double r){
double area;
area = PI*pow(r, 2d);
return area;
}
Notice that π is supported with the constant PI in Java.
The area of an ellipse is:
Area = π x y
Where x is the shortest radius and y is the longest radius.
This is implemented as:
public static double areaOfEllipse(double x, double y){
double area;
area = PI*x*y;
return area;
}
The surface area of a sphere is:
Area = 4 π r²
This is implemented as:
public static double surfaceAreaOfSphere(double r){
double area;
area = 4d*PI*pow(r, 2d);
return area;
}
The surface area of a cone is as follows, where r
is the radius of the bottom circle and h
is the height of the cone.
Area = π r (r + √(h² + r²)
This is implemented as:
public static double surfaceAreaOfCone(double r, double h){
double area;
area = PI*r*(r + sqrt(pow(r, 2d) + pow(h, 2d)));
return area;
}
The surface area of a cone is as follows, where r
is the radius of the circle and h
is the height of the cylinder.
Area = 2 π r (h + r)
This can also be expressed as two times the area of a circle pluss the area of the folded out rectangle with sides the circumfence of the circle and the height if the rectangle.
Area = 2 areaOfCircle(r) + areaOfRectangle(2 π r, h);
This is implemented as:
public static double surfaceAreaOfCylinder(double r, double h){
double area;
area = 2d * areaOfCircle(r) + areaOfRectangle(2d * PI * r, h);
return area;
}
Here we call the functions implemented earlier to calculate the area of a circle and rectangle.
Lets do an analysis to check the library is correct. In the folder area/area/
run:
progsbase analyze
If this returns without error, the library is both valid Java and valid to progsbase.
Now we can set the version to finalized in info.json
. Remove -SNAPSHOT
making the version 0.1.0
.
Run the following command to upload the library to the online program database, where it will be available in all supported languages, currently the 9 shown earlier.
In the folder area/area/
run:
progsbase upload
You can see and test the results here:
https://repo.progsbase.com/repoviewer/no.inductive.idea10.programs/area/0.1.0
The online database supports executing the functions directly in the browser. The way this is done is by loading the translated JavaScript version and generating input and output fields in HTML.
Want to see a more complex example? check out the Industrial Case: Replacing a Barcode Solution at Inkeria
We would be more than happy to help you. Our opening hours are 9–15 (CET).
📞 (+47) 93 68 22 77
Nils Bays vei 50, 0876 Oslo, Norway