
- •Foreword
- •1. Introduction
- •2. Culture Shock
- •3. Preliminaries
- •Notation Used in This Book
- •Terminology
- •Sentences (statements)
- •Word Formation (tokenizing rules)
- •Numbers
- •Characters
- •Valence of Verbs (Binary and Unary Operators)
- •How Names (Identifiers) Get Assigned
- •Order of Evaluation
- •How Names Are Substituted
- •What a verb (function) looks like
- •Running a J program
- •The Execution Window; Script Windows
- •Names Defined at Startup
- •Step-By-Step Learning: Labs
- •J Documentation
- •Getting Help
- •4. A First Look At J Programs
- •Average Daily Balance
- •Calculating Chebyshev Coefficients
- •5. Declarations
- •Arrays
- •Cells
- •Phrases To Memorize
- •Constant Lists
- •Array-creating Verbs
- •6. Loopless Code I—Verbs Have Rank
- •Examples of Implicit Loops
- •The Concept of Verb Rank
- •Verb Execution—How Rank Is Used (Monads)
- •Controlling Verb Execution By Specifying a Rank
- •Examples Of Verb Rank
- •Negative Verb Rank
- •Verb Execution—How Rank Is Used (Dyads)
- •When Dyad Frames Differ: Operand Agreement
- •Order of Execution in Implied Loops
- •A Mistake To Avoid
- •7. Starting To Write In J
- •8. More Verbs
- •Arithmetic Dyads
- •Boolean Dyads
- •Min and Max Dyads
- •Arithmetic Monads
- •Boolean Monad
- •Operations on Arrays
- •9. Loopless Code II—Adverbs / and ~
- •Modifiers
- •The Adverb Monad u/
- •The adverb ~
- •10. Continuing to Write in J
- •11. Boxing (structures)
- •Terminology
- •Boxing As an Equivalent For Structures In C
- •12. Compound Verbs
- •Verb Sequences—u@:v and u@v
- •Making a Monad Into a Dyad: The Verbs [ and ]
- •Making a Dyad Into a Monad: u&n and m&v
- •13. Empty Operands
- •Execution On a Cell Of Fills
- •Empty cells
- •If Fill-Cells Are Not Enough
- •14. Loopless Code III—Adverbs \ and \.
- •15. Verbs for Arithmetic
- •Dyads
- •Monads (all rank 0)
- •16. Loopless Code IV
- •A Few J Tricks
- •Power/If/DoWhile Conjunction u^:n and u^:v
- •Tie and Agenda (switch)
- •17. More Verbs For Boxes
- •Dyad ; (Link) And Monad ; (Raze)
- •Dyad { Revisited: the Full Story
- •Split String Into J Words: Monad ;:
- •Fetch From Structure: Dyad {::
- •Report Boxing Level: Monad L.
- •18. Verb-Definition Revisited
- •What really happens during m :n and verb define
- •Compound Verbs Can Be Assigned
- •Dual-Valence verbs: u :v
- •The Suicide Verb [:
- •Multi-Line Comments Using 0 :0
- •Final Reminder
- •The Obverse u^:_1
- •Apply Under Transformation: u&.v and u&.:v
- •Defined obverses: u :.v
- •An observation about dyadic verbs
- •20. Performance: Measurement & Tips
- •Timing Individual Sentences
- •Compounds Recognized by the Interpreter
- •Use Large Verb-Ranks! and Integrated Rank Support
- •Shining a Light: The J Performance Monitor
- •21. Input And Output
- •Foreigns
- •File Operations 1!:n; Error Handling
- •Treating a File as a Noun: Mapped Files
- •Format Data For Printing: Monad And Dyad ":
- •Format an Array: 8!:n
- •Format binary data: 3!:n
- •printf, sprintf, and qprintf
- •Convert Character To Numeric: Dyad ".
- •22. Calling a DLL Under Windows
- •Memory Management
- •Aliasing of Variables
- •23. Socket Programming
- •Asynchronous Sockets and socket_handler
- •Names and IP Addresses
- •Connecting
- •Listening
- •Other Socket Verbs
- •24. Loopless Code V—Partitions
- •Find Unique Items: Monad ~. and Monad ~:
- •Apply On Subsets: Dyad u/.
- •Apply On Partitions: Monad u;.1 and u;.2
- •Apply On Specified Partitions: Dyad u;.1 and u;.2
- •Apply On Subarray: Dyad u;.0
- •Apply On All Subarrays: Dyad u;.3 and u;._3
- •Extracting Variable-Length Fields Using ^: and ;.1
- •Example: Combining Adjacent Boxes
- •25. When Programs Are Data
- •Calling a Published Name
- •Using the Argument To a Modifier
- •Invoking a Gerund: m`:6
- •Passing the Definition Of a Verb: 128!:2 (Apply)
- •Passing an Executable Sentence: Monad ". and 5!:5
- •26. Loopless Code VI
- •28. Modifying an array: m}
- •Monad I.—Indexes of the 1s in a Boolean Vector
- •29. Control Structures
- •while./do./end. and whilst./do./end.
- •if./do./else./end., if./do./elseif./do./end.
- •try./catch./catcht./end. and throw.
- •return.
- •assert.
- •30. Modular Code
- •Locales And Locatives
- •Assignment
- •Name Lookup
- •Changing The Current Locale
- •The Shared Locale 'z'
- •Using Locales
- •31. Writing Your Own Modifiers
- •Modifiers That Do Not Refer To x. Or y.
- •Modifiers That Refer To x. Or y.
- •32. Applied Mathematics in J
- •Complex Numbers
- •Matrix Operations
- •Calculus: d., D., D:, and p..
- •Taylor Series: t., t:, and T.
- •Hypergeometric Function with H.
- •Sparse Arrays: Monad and Dyad $.
- •Random Numbers: ?
- •Computational Addons
- •Useful Scripts Supplied With J
- •33. Elementary Mathematics in J
- •Verbs for Mathematics
- •Extended Integers, Rational Numbers, and x:
- •Factors and Primes: Monad p:, Monad and Dyad q:
- •Permutations: A. and C.
- •34. Graphics
- •Plot Package
- •2D Graphics: the gl2 Library
- •Displaying Tabular Data: the Grid Control
- •3D Graphics: OpenGL
- •35. Odds And Ends
- •Dyad # Revisited
- •Boxed words to string: Monad ;:^:_1
- •Spread: #^:_1
- •Choose From Lists Item-By-Item: monad m}
- •Recursion: $:
- •Make a Table: Adverb dyad u/
- •Cartesian Product: Monad {
- •Boolean Functions: Dyad m b.
- •Operations Inside Boxes: u L: n, u S: n
- •Comparison Tolerance !.f
- •Right Shift: Monad |.!.f
- •Generalized Transpose: Dyad |:
- •Monad i: and Dyad i:
- •Fast String Searching: s: (Symbols)
- •Fast Searching: m&i.
- •CRC Calculation
- •Unicode Characters: u:
- •Window Driver And Form Editor
- •Tacit Programming
- •36. Tacit Programs
- •37. First Look At Forks
- •38. Parsing and Execution I
- •39. Parsing and Execution II
- •The Parsing Table
- •Examples Of Parsing And Execution
- •Undefined Words
- •40. Forks, Hooks, and Compound Adverbs
- •Tacit and Compound Adverbs
- •Referring To a Noun In a Tacit Verb
- •41. Readable Tacit Definitions
- •Flatten a Verb: Adverb f.
- •Special Verb-Forms Used in Tacit Definitions
- •43. Common Mistakes
- •Mechanics
- •Programming Errors
- •44. Valedictory
- •45. Glossary
- •46. Error Messages
- •47. Index
43. Common Mistakes
Mechanics
Watch out for Adjacent Numbers
>:"0 1{y
fails because the 0 and the 1 are considered part of the same list. Use >:"0 (1{y) or >:"0 ] 1{y .
Names in Sequence Do Not Form a List
0 1 is a 2-element list, but 0 y is an error even if y has the value 1 . Use 0,y .
Remember Right-to-Left Evaluation When You Use J as a Desk Calculator
J makes a great desk calculator, but you have to remember to translate from mathematical notation to J correctly. 5 - 2 + 1 is 2, not 4 .
How to Remember the Monads {. {: }. }:
Remember that { means take (x takes from y), so } must be drop. The single-dot means beginning, and the double-dot means end. So, }. means 'drop the first item'.
How to Remember #. and #:
The single-dot produces a single (atomic) result; the multiple-dot produces a list.
Remember the Operand Order in e. i. and |
The normal J convention is that a dyad's y operand is the one that is more 'data-like' and its x operand is more 'control-like'. Thus, in x i. y, x is a table and y is one or more values to be looked up in the table. By this convention, x e. y is backwards: y is the table and x is the values.
Similarly, x | y seems backwards from x % y .
Leave a Space Before : When Used Alone
When you use : or . as a conjunction, you must remember to leave a space before the : or . so it will not be interpreted as an inflection. The following are all errors:
3:0, (+/ % #):* , and +/.* .
Use =: for Assignments Within Scripts
Code that runs perfectly well from the keyboard may not work if you put it into a script (.ijs) file. The problem is usually that you have used =. for some assignments. Entered from the keyboard, =. gives a public assignment, but to get the same effect in a script, you need to use =: .
241
Pasting Into an .ijx Window Does Not Execute
Remember that when you paste a block of text into an .ijx window, that text shows up in the window but it is not executed. To execute the text, you need to select it and then use Run|Selection.
Don't Mix elseif. and else. in the Same Structure
The control structure if./do./elseif./do./else./end. is not legal. Once you have used an elseif. you are not allowed to code else.; use elseif. do. instead of else. (the omitted condition always tests true).
Programming Errors
Remember the Asymmetry of Dyad ;
x ; y always boxes x, but it boxes y only if y is unboxed. This gives you what you want when the operands are unboxed:
1 ; 2 ; 3 +-+-+-+ |1|2|3| +-+-+-+
But when the operands are boxed, you may be surprised at the result:
(<1) ; (<2) ; (<3) +---+---+-+ |+-+|+-+|3| ||1|||2|| |
|+-+|+-+| | +---+---+-+
To have the last operand boxed, you should box it explicitly:
(<1) ; (<2) ;< (<3) +---+---+---+ |+-+|+-+|+-+| ||1|||2|||3|| |+-+|+-+|+-+| +---+---+---+
Don't Give Two Operands to a Monadic Verb
When you start writing long tacit programs, you are likely to have trouble keeping track of whether a verb is being executed monadically or dyadically. Suppose that x is a set of observations and y is a set of weights, and you want to weight each observation and divide by the total weight. You might try
x (* % +/) y
but that isn't right—the sum of the weights is +/ y and this is going to execute
x+/ y . What you meant was
x(* % +/@:]) y
Some rules to remember: a train comprising an odd number of verbs is a fork, which can be invoked monadically or dyadically. The first, third, etc.… verbs, including the
242
last, are all executed with the same valence as the fork itself, and their operands are all the same, namely the operands of the fork itself. The second, fourth, etc.… verbs are all executed dyadically, with operands that are results of other verbs in the train.
A train comprising an even number of verbs is a hook. The first verb in the hook is always executed dyadically; the rest, taken as a train, are executed monadically on the y operand of the hook.
If any part of your train requires simultaneous access to the x and y operands of the train, you must make the train a fork rather than a hook.
Use @: Unless @ Is Necessary
u@:v has infinite rank, while u@v has the rank of v . If you don't see what difference this makes, you should drop what you are doing and read the chapter on "Compound Verbs". For practical programming, you should be in the habit of using @: unless you need u to be executed on each individual result-cell of v, in which case you may use @ . The most common uses of @ are u@> to execute u on the contents of each box in a list, and <@v to box each individual result-cell of v .
Put Parentheses Around Compounds Inside Other Compounds
A modifier is greedy about what it takes for its left operand, hoovering up everything until it hits a left parenthesis or unmodified verb. For example, if you want to add 2 to y and then double the result,
+: @: 2&+ y
is going to disappoint you, because it is executed as (+:@:2)&+ y which isn't even legal. You meant +: @: (2&+) . Be liberal in your use of parentheses inside compounds. You may omit the parentheses around the leftmost compound—another way to write the above would have been 2&* @: (2&+)—but you won't regret putting parentheses around all compounds, especially when you go to change your code.
I find it easy to forget the parentheses when one of the verbs is something like +/ that I use so much that I think of it as a primitive. When something like >: @: +/ fails I am brought back to reality and I remember to write >: @: (+/) .
A Verb Is Always Executed, Even If Its Operand is Empty
J's primitives are defined to produce reasonable results when given empty operands. You should do as well with the verbs you write. Remember that if a verb has an operand with no cells, the verb is still executed once, on a cell of fills. The chapter "Empty Operands" explains what happens.
Dyad -: Does Not Check the Type of Empty Operands
Be aware that getting a result of 1 from x -: y does not guarantee that x and y are equivalent. If they have the same shape and are empty, they are considered to match even if they have different types. Subsequent operations such as {. would reveal the fact that the values are different, even though they 'match'.
243
x u/ y Applies u to Cells of x
To get x u/ y right, remember that it applies u to cells of x and the entire y . The rank of the cells of x is given by the left rank of u; use u"n/ to set the cell-rank of x .
Modifiers That Refer To y. Have Monadic and Dyadic Valences
If your modifier contains x. or y., its text defines a verb which is executed when its noun operands are known. This verb, like any explicit verb, can have both monadic and dyadic versions, separated by a line containing just a ':' character. If you want the modifier to have a dyadic form, you must code one (by default the verb will be monadic only).
Tacit Code Does Not Simply Replace a Name By Its Definition
It is easy to develop an incorrect mental picture of how tacit programs are executed. One common error is to think that names are replaced by their definitions before a sentence is executed, in other words that if you have
plus =: + then a sentence
1 plus 2
is converted to 1 + 2 and then executed. This notion immediately leads to confusion when you encounter
mean =: +/ % # and you expect
mean 1 2 3 4 5 to be executed like
+/ % # 1 2 3 4 5
which is not how it works. If you find yourself making this error, read the chapters on Tacit Programming to learn what really happens.
As a stopgap, you can imagine that each name's value is enclosed in parentheses before it is substituted. This still isn't exactly right but it gets you the right result in all situations you are likely to encounter. You would imagine that the sentence above is executed as
(+/ % #) 1 2 3 4 5
which gives the correct answer. You must realize that (+/ % #) is a fork, with its own rules for processing its operands.
244