Skip to content

ASWI Programming Standards; some Whys.

Vector 9:3, page 101

standards development practice

Transcribed from the printed issue; not yet reviewed. Read it in the PDF of the issue, page 101

Vector 8.2 published our ASWI standards for programming and documentation. This publication listed our proposal as a number of prescriptions without elaborating upon the reasons behind the various ideas.

It is not always easy to determine what is obvious in a proposal and what is not. In the discussions we had in reaching the ASWI standard some points were discussed at length, while others were taken for granted immediately among the participants. But some reactions from Dutch users among whom we circulated a preliminary version showed still different attitudes. This shows — not surprisingly, of course — how different experiences make up for the initial acceptance or rejection of different points.

Recently, Ray Cannon reacted in Vector 8.4 against various parts of the ASWI proposal. I am pleased to see his comments as they help us to pinpoint the most "offensive" parts and hence enable us to select those points which need more explanation, or which need to be changed.

In this sequel I will explain some of the considerations regarding:

  • SID in user-functions
  • SID in sub-functions
  • SID in standard functions
  • lowercase characters
  • length of names of local variables
  • miscellaneous

SID in User-functions

Let us start with the SID in the name of functions. ASWI proposes to start the names of all user-functions with a 3-letter code, the SID (System IDentification). First of all, this proposal did not descend from heaven as a purely hypothetical idea. On the contrary, it is the formalisation of a long-standing practice at Philips and a big bank in Holland during more than a decade. Subsequently that proposal did not generate any discussion in the ASWI committee (or, as yet, elsewhere), because those users were already very satisfied with this practice. This alone, however, doesn’t make the benefits obvious, and Ray’s objection indicates that some elaboration of the reasons is indeed required.

Yes, in extreme cases, it is harder to find a particular function if all the functions in the workspace start with the same SID. But in general, a WS is not only filled with functions with the same SID. In my simulation workspace for example, one finds DLG-functions to manage the user-dialogues (copied from workspace DLG), one finds MDF-functions (from workspace MDF with Machine-Dependent-Functions), one finds GRF-functions (from a graphics workspace), and so on. Now a )FNS or a ⎕NL 3 beautifully lists each of those groups together. So this is much more of a help than a hindrance.

Moreover, I see this recipe applied in real-world applications often enough (for example in the file-workspaces of APL.68000 where the Atari-functions are called STREAD, STTIE, STWRITE and the Macintosh functions are called MTIE, MREAD and MWRITE). Nor were there any objections in the past to the names of the functions TSTEXPONENTIAL, TSTNORMAL and TSTPOISSON in my workspace TSTDISTR (this workspace tested against various distributions). Nor with the functions RNDEXPONENTIAL, RNDNORMAL and RNDPOISSON in my workspace RNDVARTS (this workspace generated random numbers according to different distributions).

So, again, I would say that those facts indicate that application of a SID was considered useful long before our proposal.

Furthermore, I wouldn’t object if functions in the APL Statistical Library had for example the prefix DES for all descriptive statistical functions and had the prefix TST for all testing functions, or even TNR for a collection of functions with statistical tests which assume normal-distributed variates and TOT for other tests. I must admit that I can also imagine that one prefers MEAN instead of DESMEAN and SPEARMAN instead of TSTSPEARMAN because MEAN and SPEARMAN are so well established names that one doesn’t want to burden the user with those prefixes. So this example is an in-between, for which there is probably as much in favour of the prefix as there is against it.

Ray is quite right that sometimes a SID- prefix in the name is undesirable, but I don’t think that APL programmers are much disturbed by such a SID-prefix. However I can imagine that a SID prefix might be undesirable for the end-user sometimes …

  • not if the end-user doesn’t see the main-program because the workspace starts in ⎕LX there is no problem.
  • not if the end-user has to activate just a few functions like LITRETRIEVE and LITSEARCH in a literature system, although I must admit that here our recipe might be debatable.
  • but yes, I definitely agree that …

    LITRETRIEVE LITALL LITBOOKS LITOF 'BROWN'
    

    is ludicrous and should be…

    RETRIEVE ALL BOOKS OF 'BROWN'
    

So in general I would say that a SID prefix is often very useful and that such a proposal in ASWI is merely a formalisation of a long-standing practice. I must admit however, that our proposal was probably stated somewhat too categorically and that it should have left some room for exceptions.

SID in Sub-functions

For imported subfunctions there is nothing wrong with using a SID-prefix either. Regarding Ray’s statement "a utility should be independent of its origin" I would like to comment that a utility should not be independent of its task; and its task determines its prefix. I found it very useful that the graphics of STSC started with ⎕G and the file functions with ⎕F and the window functions with ⎕W. Again, nothing purely theoretical, but a real-life implementation before our proposal came to life.

Now what about a prefix for IOTA? If I knew why Ray programmed a function IOTA, I wouldn’t have problem finding a proper SID. Was the intention to simulate standard APL functions among which was IOTA? Then why not APLIOTA, APLESTI, APLRHO, and APLTAKE? Then the SIM-workspace would either contain an APLIOTA or a SIM_IOTA. The name APLIOTA indicates that this is the original utility from the APL-workspace. And the name SIM_IOTA would indicate that the function is not any longer working as one might expect, because it is more or less subtly adapted for use in the SIM-workspace.

The advice from ASWI is to change the name of an imported subfunction as soon as one tampers with it to adapt it for the particular application in which it is imported. Ray comments to that "a true utility’s name should be independent of its origin, if the origin of a function is important, then comment it, don’t clutter up the space name". To this I would say: if you adapt a utility for a particular application it is not a "true utility" any more. It is exactly to warn against unsuspected deviant behaviour that this proposal will protect you. Comments alone are certainly not powerful enough (do you consult the comments every time you invoke a utility? For many I don’t).

SID in standard functions

The only case in which I have some real misgivings about the ASWI standard is about the SID-proposal regarding the standard names like SID∆BEGIN, SID∆ABSTRACT, SID∆DESCRIBE, SID∆HOW etcetera. There was much debate in the ASWI committee about this.

  1. One group argued that they often merged several workspaces together. If no prefix was used, with each new workspace copy the previous BEGIN, ∆DESCRIBE and ∆HOW would be replaced. As they wanted to consult all the descriptions they preferred a prefix so one could still recognise all descriptions.
  2. The other group argued that most of those ∆FUNCTIONS are used by novices who don’t know the workspace. So they don’t know the SID either and they just want to load the workspace and type ∆ABSTRACT or ∆DESCRIBE to see what they have in their hands without bothering about any SID.

We finally opted for the first case, but our committee was not unanimous.

Lower-case Characters

For global variables ASWI requires that a name consists of lower-case characters preceded by the SID, and for sub-global variables a name of lower-case characters preceded by SID_. Ray is right that it is useful to mention the alternative of underscored characters for implementations without lower-case characters. We didn’t do this because basically our proposal was drawn for a project of shareware program development using APL2/PC and APL.68000. However, to take other APL implementations into account would give our proposal a broader impact. So I propose to mention in the ASWI committee the alternative of underscored characters in the next version.

Length of Names of Local Variables

ASWI requires that names of local variables do not exceed 4 characters. Although the particular number 4 is somewhat arbitrary of course (why not 5, or 3?) my experience is that APL functions tend to lose their surveyability rapidly with lengthy names. As most of the APL functions and operators occupy 1 character, a variable of, say, 4 characters already dominates a code-line much more than warranted. So my personal preference is to use 1 or 2 character names in small functions, and highly incidental 3 or 4 characters in bigger functions. It is my experience that "natural names" can be abbreviated to 2 or 3 characters and still be recognisable. The ASWI committee doesn’t share Ray’s fear that shortening a "natural name" will diminish readability. We believe the contrary.

Miscellaneous

The ASWI standard ends with a Miscellaneous paragraph with "a few remarks…on APL programming practice". Here we suggest that "good" APL-functions…

5. work for missing left argument (default) and don’t crash for empty arrays.

6. receive data in the right argument and control in the left.

Both suggestions are gross over-simplifications. They were intended to steer APL programmers towards some preferred standard practice. These remarks were not intended to mean literally that either…

  • a function which desperately needs data in its left argument is a bad function.
  • a function which has a default for a missing left argument is always a good function.
  • a function which has control and data in the left and right arguments respectively is always a good function.
  • a function which has data in both the left and the right argument is always a bad function.

What we did want to accomplish was to force a programmer to reflect about his design and to wonder…

  • "is there a compelling reason why I want to deviate from this suggestion and have no default for the left argument?" (if so, fine). By the way, an empty vector ('') is a suitable substitute for a missing left argument in implementations without ambivalent functions. I will propose in the ASWI committee to mention the alternative of '' in the next version.
  • "if I have two types of information — one processed data and the other control information which steers the function — is there a compelling reason not to distinguish those types and not to present the controlling information in the left and the processed data in the right argument?" If there is a compelling reason to deviate, then fine again.

I hope to have clarified most of the points in the ASWI proposal to which Ray objects. We do indeed think that the ASWI proposals aid readability and maintainability. The recipes are not as ephemeral and hypothetical as Ray probably thought. Most of them were derived from our own everyday experience. As to Ray’s suggestion of applying them to see if they help or hinder, we can assure him that we will do so, and have done so.

Ray’s comments have been worthwhile contributions to improve our standards with regard to:

  • giving a little bit more leeway to omit a prefix SID in user-functions.
  • reconsidering the SID in standard functions.
  • mentioning underscored characters as the alternative to lower-case characters.
  • mentioning the ''-alternative to missing left arguments.

F.H.D. van Batenburg,
Leyden University Institute for Theoretical Biology,
Kaiserstraat 63, Leiden,
Holland