Software Engineers Handbook/Language Dictionary/Smalltalk

Smalltalk

edit

Here is the wikipedia entry.

Type

edit

Smalltalk is a full procedural object oriented language.

All arguments are conceptually references to objects. All implementations, however, represent small integers within the pointer rather than allocating a physical object for each.

The language does not require implementations to support proper tail recursion, and none of them do.

It was in connection with Smalltalk that the term "object-oriented" first appeared, although the first object-oriented language was Simula 67.

Execution Entry Point

edit

Smalltalk programs typically don't have a single entry point but are saved as image files (object memory snapshots). When started, such image files just continue to do whatever they were doing when they were saved.

General Syntax

edit

Smalltalk expressions consist of message sends and variable assignments.

a := b := c + 2 * (x even ifTrue: [y] ifFalse: [z negated]).

Message sends can be either

  • unary (in example above: even, negated)
  • binary (+, -, etc.)
  • keyword (ifTrue:ifFalse:)

Unary messages bind most strongly, then come binary messages, then keyword messages. Binary messages are evaluated from left to right, there is no operator precedence. Assignments are evaluated right to left. Message expressions can be parenthesized. Angle brackets [] denote blocks. Blocks are first-level objects and can be assigned and passed as parameters.

Comments

edit

Smalltalk comments are delimited with the double quote character:

"This is a comment"

They can span multiple lines.

Variable Declarations

edit

Variables have to be declared, but they don't have type information. Method arguments often have their intended role or the expected class in their name.

Temporary variables:

| x y total subtotal |

Method arguments:

addAmount: aDecimalNumber purpose: aString

Block arguments:

[:a :b | a < b]

Block execution:

[:a :b | a < b] value:1 value: 2

Instance and class variables are declared within the class definition message (details vary between implementations):

Object subclass: #MyClass
  instanceVariableNames: 'name owner additionalData'
  classVariableNames: 'DataRepository'

Statically scoped variables (globals and class variables) are declared by executing expressions which create them in the system. Examples for this are the class definition messages.

Method Declaration/Implementation

edit

Programmers write methods on classes. A class is a Platonic pattern of which objects can be made as instances. In Smalltalk, each class is also realized as an object, supporting the protocol to make and return a new instance (new). Classes have global names; all global names start with capital letters.

Note that programming language Self inherits many of the good features of Smalltalk but is conceptually simpler by eliminating the concept of a class.

Scope

edit

Smalltalk has global variables, instance variables, temporary variables (to methods), and parameters (to methods). Blocks also can have parameters. In most modern implementations, blocks can also have their own temporary variables. There is also something called pool variables, they have the same lifetime as global variables, but just aren't accessible except in classes that explicitly include the pools (and in hiers of those classes). Instance variables are not accessible outside the object they belong to; however, programmers often provide access methods, even to variables intended to be private.

In practice, pool and global "variables" are often used for constants.

Conditional Statements

edit

Conditional statuements are normal message expressions. The message receiver is a Boolean value (true or false), and the arguments are blocks.

a < 10 ifTrue: [self handleSmallValue]. 
self hasValidInput
  ifTrue: [self processInput]
  ifFalse: [self displayInputFormatError]

Looping Statements

edit

Loops are done by sending messages to blocks:

[stream atEnd] whileFalse: [self process: stream nextLine]
[a < limit] whileTrue: [a := a + 1]

Iterations over collections are performed with 'do:'

anArray do: [:each | self doSomethingWith: each]

Counting loops look like this:

1 to: 10 do: [:i | Transcript show: i printString; cr]

Output Statements

edit

As most Smalltalk systems are not command-line oriented, output to "stdout" as such is not normally used. However, Smalltalk systems normally have a logging window (the Transcript) into which output can be written:

Transcript show: 'Hello, world!'; cr

Containers

edit

The standard Smalltalk library includes an extensive collection of classes of mutable collections: Array, OrderedCollection (in which it is efficient to append or delete from either end, and in which storage is economical (as an array rather than a linked list or a tree), Set, Bag, Dictionary, IdentityDictionary, SortedCollection. Collections support useful second-order functions collect: (like map in Lisp), select:, detect:, and reject:, and the second-order procedure do:.

Since Smalltalk is dynamically typed, so are its containers; they may point to any mix of objects of any types.

Algorithms

edit

<List algorithms or references to lists of algorithms available natively for this language. List ways to incorporate algorithms if they are not native to the language. Or, if not available, describe that.>

Garbage collection

edit

Garbage collection is automatic.

Some implementations support weak references.

Physical Structure

edit

Traditional Smalltalk-80 systems consist of:

  • runtime engine (interpreter or JIT plus primitives and platform interfaces)
  • image file
  • 'changes' file (log of source code and evaluated expressions)
  • 'sources' file (source code for the methods in the initial image)

More modern systems often split up the runtime engine into an executable plus shared libraries, and may have additional files for version control systems etc.

Tips

edit

Don't try too hard to keep your old habits. You can write Pascal-style programs in Smalltalk, but they won't be good Smalltalk programs.

Keep behavior with those objects most central to it. It's often good to anthropomorphize your objects and write comments in the first person such as:

addEntry: anEntry
  "Add anEntry to my list of entries. If the entry conflicts with another entry, I will drop the older one."
  
  entries removeAllSuchThat: [:oldEntry | anEntry conflictsWith: oldEntry].
  entries add: anEntry

Web References

edit

A great resource of Free Books on Smalltalk [1]

Books and Articles

edit

<List additional books and articles that may be helpful. Please include for what level reader the references are appropriate. (beginner/intermediate/advanced)>

Goldberg and Robson

Byte Magazine special issue on Smalltalk, 1979.