S T R U C T O R I Z E R - User Guide
Elements > Program / Sub / Includable

The bare diagram

When you start Structorizer or create a new diagram, then you will be presented an empty diagram with dummy name "???":

Empty diagram

Double-click the question marks and fill in a sensible name in the central text field superscribed with "Diagram name / function signature" of the element editor that will pop up. (Before release 3.27, this was the upper one out of only two text areas.)

  • The name should represent the aim of your algorithm.
  • The name should be an "identifier", i.e.:
    • The name should not contain spaces: THIS IS NOT A GOOD ALGORITHM NAME.
    • If the name is to consist of several words, you may fill the gaps between the words with underscores: THE_ALGORITHM_NAME_SHOULD_BE_CONTIGUOUS.
    • Ideally, the algorithm name should start with a letter and only contain letters, digits and underscores (identifier syntax).

Also make sure to fill in the lower text field (superscribed "Comment") with a description of what the algorithm is good for and how to use it.

Editor mask for Root element

The framing (or root) element of a Nassi-Shneiderman diagram represents either a program, a (callable) subroutine, or an includable diagram (also see Type setting).

  • A program means a standalone algorithm (an application) as being executable as a process on the operating system level. It usually communicates with the user via input and output instructions.
  • A subroutine typically means a parameterised algorithm that can be used to perform some subordinate task within a program or another routine, e.g. to calculate the sine of an angle, the square root of a number or to rotate the turtle in the Turtleizer tool by a certain number of degrees. Subroutines are usually provided with values via parameters (on calling) and they possibly return a result value to the calling level. Whereas the functions and procedures just mentioned are already built in, on decomposing a complex algorithmic problem you will usually find it helpful to define your own subroutines. Depending on whether they return a value or not, subroutines are often subdivided into
  • procedures, not returning a value (and rather effectuating some impact to the environment);
  • functions, supposed to return a result (usually without further impacts or side-effects).
  • An includable diagram (as introduced with release 3.27) is typically a collection of constant definitions, type definitions, and declarations of variables, which are to be shared e.g. among a main diagram and some of its subroutine diagrams. In order to get hold of the defined data, a diagram must include the includable diagram by adding it to its include list, which is the faintly yellowish upper text field in the editor (superscribed "Diagrams to be included", see image above).

Structorizer allows you visually to distinguish whether a created diagram is meant to be a program, a subroutine, or an includable diagram - they differ in the shape of the surrounding box: 

  • A program diagram has rectangular shape,
  • the corners of a subroutine diagram will be rounded,
  • an includable diagram has two bevelled corners.

How to set the type of the diagram?

Just select the appropriate one of the menu items "Diagram => Type => Main" / "Diagram => Type => Sub" / "Diagram => Type => Includable" (see screenshot) or one of the toolbar buttons boxed red in the screenshot (cf Settings/Type).

Menu items and toolbar buttons to switch among program and subroutine

When you start with a new diagram, it will initially be a program. The following images show you the computation of the factorial both as a program (left) and as a function (right). Note that the assignment to variable result is one of three supported value return mechanisms (see last paragraph below).

Diagrams to compute the factorial
As Program As Function
Editor mask for Root element with Factorial description Edit mask for Root element containing the factorial function description

Factorial algorithm as program

Factorial algorithm as function

In order to allow you a subroutine simulation at the top level (i.e. without calling context), the Executor will pop up an input dialog for every function parameter before the execution and an output dialog showing the computed result on termination. (But this is only the case while you execute a subroutine diagram at the top level.)

Diagram header

If the diagram is a program (or an includable diagram, only release 3.27 and beyond) then the text field is supposed to contain just its name. A program name should be an identifier as described above, i.e. a word consisting of letters, digits, and underscores, beginning with a letter or underscore. It should not contain blanks.

A subroutine header, however, is supposed to contain more information than just the name. The subroutine name (an identifier as described above) is to be followed by a parameter list. A parameter list - in its simplest form - is a pair of parentheses containing a series of parameter names, separated by comma or semicolon (see example above).

A typed subroutine header may have Pascal syntax (where each parameter name is followed by a colon and a type name. The parameter specifications are to be separated by semicolons. If several parameters are of the same type, they may be grouped to a comma-separated list of their names, followed by the common colon and type name; note the semicolon between parameter groups of same type! The result type - if any - follows the parameter list, separated from it by a colon), e.g.

functionName(var1, var2: Cardinal; var3: Double): Double

or C/Java syntax (where the name of any parameter follows its type name; all parameter specifications are separated by commas, a grouping of parameters of the same type is not possible, semicolons are not allowed; the result type precedes the function name), e.g.

double functionName(int var1, int var2, double var3)

or modern BASIC-like syntax (very similar to Pascal syntax, except that the keyword as is to be used instead of the colon and semicolons are not allowed) , e.g.:

functionName(var1 as Integer, var2 as Integer, var3 as Double) as Double

All three forms will be accepted by Structorizer and converted to proper function headers on code export if possible.

Return mechanisms

In order to return a value from a function diagram, you have the choice among three possible mechanisms supported by Structorizer (i.e. both execution and code export):

  1. Assign the value to a variable named exactly like the subroutine (like in Pascal; in the above example you might modify the last line to: factorial <- fact);
  2. Assign the value to a variable named "RESULT", "Result", or "result" (as shown in the example above);
  3. Add a return instruction (like in C, Java, and the like; modify the last line in the above example to: return fact).

The first two of the opportunities allow to override a provisionally assigned value by subsequent instructions such that just the last performed assignment to the function name or result variable will be the final result, whereas a return instruction will immediately force the termination of the subroutine with the attached result.

You should not employ more than one of the three result mechanisms described above within the same diagram, otherwise the result may not be what you expected it to be.

Note that mechanism 1 will cause Analyser complaints if option "Check that the program / sub name is not equal to any other identifier" is enabled in the Analyser Preferences.

Includable diagrams (introduced with release 3.27)

The third diagram type differs from the types above in two important aspects:

  • it shares its defined types, constants, and declared variables with all diagrams including it;
  • it is executed at most once - from the first executed diagram that holds it in its include list.

Includable diagrams were introduced:

  • to cope with code import and export of some source languages, where global definitions, include files etc. are a common feature;
  • in order to be able to introduce compound types (aka record, struct), which require a definition possibly having to be shared between a calling diagram and a called diagram if the argument list happens to contain a parameter of such a record type.

Whereas it is okay to share types and constants, it is not recommendable to share variables this way. Indeed, the use of shared (global) variables should be avoided on algorithm design, because

  • it hides the flow of data (if accessed bypassing the parameter lists),
  • it bears always the risk of unwanted interference,
  • it drastically limits the general usability of the algorithm.

Example of an includable diagram, defining a constant, providing a shareable variable and writing a text once (only on the first include within a program execution):

Includable diagram with three instructions

Ideally, the diagrams to be included (the "includable diagrams") should only contain constant definitions, type definitions, variable declarations, variable initializations, and the like. The following example demonstrates that the constant ultimateAnswer defined in diagram "GlobalDefinitions" is recognized and therefore highlighted in the importing diagram "ImportCallDemo" as if it were introduced by the importing diagram itself (which is not the case because the preceding assignment "ultimateAnswer <- 3" is disabled - if it were enabled you would be warned of an illegal attempt to modify a constant).

Example of a diagram with an include list and the included diagram

The right diagram presents the list of the names of diagrams to be included. The list is positioned above the program name or function signature and is surrounded by a bevelled box, which reminds the shape of an includable diagram. You may edit the list of diagrams to be included by filling in the yellowish top text field ("Diagrams to be included") in the editor for the dependent diagram, see below:

Program editor with includes list

Another aspect is that included diagrams may (of course) in turn include other includable diagrams. But there must never be a cyclic inclusion (e.g. diagram A includes diagram B, which in turn includes diagram A)! Analyser and Executor do their best to detect and avert such a cyclic inclusion, however.

Attribute Inspector

There is an "Attributes" button below the comment field in the element editor for Program/Sub/Includable, which opens an "Attribute Inspector" dialog where you may inspect more meta information about the diagram and set or modify some of them. For a new diagram, it might look like this:

Attribute inspector for a new diagram

You may open this dialog also via the file menu ("File => Inspect attributes...") or with key combination <Alt><Enter> from the working area:

File menu with attribute inspector entry

Since version 3.28-08 you may also activate the Attribute Inspector for any diagram located in the Arranger via the context menu of the Arranger Index (provided an item is selected).

The "Attribute Inspector" allows you to have a look at the meta information about the diagram, including paths, author, creation and modification dates, stored copyright information etc. It also shows you the counts of contained elements per type and it may present the differing associated keywords if the diagram was loaded without automatic keyword refactoring (as to be enabled in the Import Preferences):

Attribute inspector for an unrefactored diagram

By pressing the button "Compare parser keys" in such a case you may additionally  open the Parser Preferences in read-only mode such that you can compare the current preferences with the ones attached to the diagram (particularly those marked red in the Attribute Inspector):

Read-only parser perefereces from Attribute Inspector