Page Numbers: Yes First Page: 1
Heading:
June 16, 1977 10:36 AM [IVY]<KRL>document>str-lev-mem-comp-decl
Status: More or less done -- needs updating to include memory-sequence stuff, and is therefore not yet consistent. Also needs something on what is in the catalogue, and detail on how records are actually accessed in memory (i.e. Henry’s access functions)
Specification of the compaction declarations for KRL1
Along with any unit, the user can provide a compaction declaration which specifies a subset (possibly the full set) of the slots in that unit, with a declaration for each as to a specific form for the contents. One form for map-descriptors having a declared unit as their prototype is to be a record with fields corresponding to the declared fields, and contents to be interpreted according to the declarations. Such records can be accessed with the normal Seek/Match/Describe mechanisms which will be converted by the access compiler into the appropriate record accesses whenever possible (i.e. when the process description specifies simple structure-only operations, and the result description matches what is known to be stored in the field.)
The general idea (see <krl>compiling.bravo for more discussion) is that the generality of a full description is not needed for many cases. In a normal map descriptor, each filler pair consists of a name, and an anchor for the filler description. In a compacted descriptor, the fillers appear in a sequence, with the names implicit in the sequencing (as defined in the declaration). Each filler contains the minimal data structure needed to specify the desired description of the filler -- for example, a lisp pointer or anchor. The declaration tells how this is to be interpreted as a full descriptor. In addition, the declaration can specify that the filler is to be treated as a current value, even though it does not explicitly appear in that form (see <KRL>worlds.doc for more discussion of current values).
Note: Before reading further details, it may be useful to look at the examples beginning on page 4, to have some idea of how things fit together in general.
The declaration for a unit is simply a sequence of declarations for slots within that unit. The declaration for each slot specifies two orthogonal things: whether the filler is to be treated as a current value, and its type (how it is to be interpreted as a descriptor). The possiblilities are:
Anchor: The field contains an anchor handle, It is interpreted as if that anchor were the anchor for the filler of the corresponding filler pair. This is an escape back to the general description mechanism for a single filler pair.
Coreference: The field contains an anchor handle. It is interpreted as a filler containing a single coreference descriptor, with the coreference target being that anchor.
Lisp: The field contains any valid LISP pointer. It is interpreted as a filler containing a single LISP descriptor containing that pointer.
Handle: The field contains any valid LISP pointer or handle. It is interpreted as a filler containing a single Handle descriptor where the object being described is the object pointed to.
Collection: The field contains a handle to a memory-sequence. The filler is interpreted as containing a single Set or Sequence descriptor. Each of the elements of the sequence is interpreted as a description contained in an anchor of the collection descriptor. If a field is declared as a collection, then it must be further declared as:
Set or Sequence: The descriptor implied by the field
Complete or Incomplete: Corresponds to "..." in the descriptor implied by the field.
Type: A recursive application of the set of choices for types of field in general (not including current value, but including recursive use of collections), to be used in interpreting each element of the list.
In addition, there are two combined types which are unions of these types, distinguishable by the type of object actually appearing in a given instance.
Thing: If the field contains an anchor handle, it is interpreted as if it were declared as a Handle field. If it is any other LISP pointer, it is interpreted as though it were a LISP field.
Reference: If the field contains an anchor handle, it is interpreted as if it were declared as a CoReference field. If it is any other LISP pointer, it is interpreted as though it were a LISP field.
The Units used in the actual forms
The following units form the basis for the declarations which will be recognized by the initial KRL-1 system. They are entered as meta-descriptions associated with units, and are stored by the cataloguer.
# CompactionDeclaration↑1
1: HasFunctional(unit, CompactedBy, sequence fieldDeclarations)
self:
unit:
A Unit
fieldDeclarations:
SequenceOf (A CompactionFieldDeclaration with
slotName = SlotNameOf(MemberOf
(The slots from My unit)))
# CompactionFieldDeclaration↑1
1: HasFunctional(self, Field, slotName, interpretation)
self:
slotName:
A LispAtom
interpretation:↑2 A FieldDescriptor
2: Comment ("This description is treated as a template for the interpretation of each
instance of the field appearing in a compact descriptor")
# FieldDescriptor
self:
A FieldDescriptor
Categories (Type, {AnchorField, CoreferenceField, HandleField, LispField,
ThingField, ReferenceField, CollectionField})
Default(Not(A CurrentValueField))
# CurrentValueField
self: A FieldDescriptor
# AnchorField
self: A FieldDescriptor
# CoreferenceField
self:
A FieldDescriptor
# HandleField
self:
A FieldDescriptor
# LispField
self:
A FieldDescriptor
# ThingField
self:
A FieldDescriptor
# ReferenceField
self:
A FieldDescriptor
# CollectionField↑1
1: HasFunctional(self, SetFieldOf, elementDescriptor
with self = A SetField)
HasFunctional(self, SequenceFieldOf, elementDescriptor
with self = A SequenceField)
self:
A FieldDescriptor
Categories(CollectionType, {SetField, SequenceField})
Default (Not (An IncompleteCollectionField)))
elementDescriptor: A FieldDescriptor
Not(A CurrentValueField)
# SetField
self:
A CollectionField
# SequenceField
self:
A CollectionField
# IncompleteCollectionField
self: A CollectionField
The form of legal declarations
The cataloguer will recognize only declarations which fit the following form:
1: The declaration consists of a single descriptor using the functional CompactedBy appearing as a metaDescription of a unit.
2. Each of the field declarations in its second argument consists of a single descriptor using the functional Field, with its first argument being a LISP descriptor quoting the slot name.
3. The second argument of Field can contain multiple desciptors as follows:
3a. It must have one (and only one) type descriptor. This is either a simple perspective of the form An X, where X is one of the basic field types (including ThingField and ReferenceField, but not CollectionField) or a single functional using SetFieldOf or SequenceFieldOf, whose argument follows rules 3a and 3c here.
3b. It can contain the descriptor A CurrentValueField. If it does not, the field will be assumed to contain a static description.
3c. If it is defined using SequenceFieldOf or SetFieldOf, it can contain the descriptor An IncompleteCollectionField. If not, it will be assumed to be a complete collection enumeration.
3d. Other descriptors are allowed but they will be ignored.
Functions for getting information from the catalogue
This still needs to be specified (see future document on the catalogue). It will only be used by those who are doing the access compiler, or incorporation and anchoring.
Example 1:
# Student↑11: CompactedBy( Field(’idNumber, A LispField),
Field(’lastName, A LispField),
Field(’firstName, A LispField),
Field(’nickName, A LispField
A CurrentValueField),
Field(’courses, SetFieldOf(A CoReferenceField)
A CurrentValueField),
Field(’grades, SequenceFieldOf(A ReferenceField)
An IncompleteCollectionField
A CurrentValueField),
Field(’bestFriend, A CoReferenceField)
Field(’firstTeacher, An AnchorField),
Field(’favoriteTeacher, An AnchorField
A CurrentValueField))
self: A Person
idNumber: An Integer
firstName: A String
middleName: A String
nickName: A String
lastName: A String
courses: SetOf (A Course)
grades: SequenceOf(A Number)
firstTeacher: A Teacher
favoriteTeacher: A Teacher
bestFriend: A Person
Given this declaration, assuming that the compiler uses the record package in the most straightforward way, making a simple typerecord with the unit name as the type, and assuming that anchor handles are data structures, then the following record structure and description are equivalent (Note: in fact, these structures will probably be on files, the records will be fixed length sequences instead of linked lists, and the handles will be special file pointer objects):
Description:
A Student with
idNumber = 43021
firstName = "Jane"
lastName = "Doe"
nickName = Currently("Janey")
courses = {French1, History101, The requirement inUnit Drama}
grades = <A, 3.5, 98 ...>
firstTeacher = A Man
favoriteTeacher = Currently(A Woman; A GymTeacher)
Record structure
(Student
43021 "Doe" "Jane" "Janey" (#3201 #5588 #62) (#776 3.5 98) NIL #302 #555)
where the anchors pointed to are as follows:
#3201 = French1.self (i.e. the anchor in the self slot of the unit named "French1")
#5588 = History101.self
#62 = Drama.requirement (i.e. the anchor in the slot named "requirement" in the unit named "Drama")
#776 = A.self (i.e. the unit for the letter "A")
#302 = an unlabelled anchor which would print as: A Man
#555 = an unlabelled anchor which would print as: A Woman; A GymTeacher
Things to note:
1. Slots (e.g. middleName in this example) can be left out of the compaction declaration. This means that no compact map descriptor can be interpreted as specifying a filler for that slot.
2. Order is arbitrary. The order in the record follows the order in the declaration, which has no relation to the order of slots appearing in the unit.
3. The ReferenceField declaration makes it possible to mix values which are coreferences (like the letter grade A) along with those which are Lisp values (like the numerical grade 98).
4. The CoreferenceField delcaration allows both unit and slot coreferences.
5. The default is to assume complete collections (in this case, assuming the set of courses is complete)
6. If a NIL appears in a field which should contain a handle (e.g. the field for bestFriend in this example), it is interpreted as meaning that no value was filled in. This is equivalent to simply not mentioning that slot in the map descriptor.
Problem: How to distinguish NIL from empty field in LISP and HANDLE types (assuming that NIL means empty for other types)
7. This example does not use the HandleField declaration, or its generalization, ThingField. This is because those declarations are used only when the thing being described is actually a machine (KRL-structure) entity itself. These will apear only in descriptions at the meta-layer which are talking about other objects appearing within the system.
Example 2:
# Entity↑11: CompactedBy( Field(’primaryAnchor, A HandleField),
Field(’relatedEntity, A CoReferenceField),
Field(’funnyField, A LispField),
Field(’identifiedAnchors, SetFieldOf(A HandleField)
A CurrentValueField),
Field(’friend, An AnchorField))
self:
primaryAnchor: An Anchor
identifiedAnchors: SetOf(An Anchor)
relatedEntity: An Entity
funnyField: A LispObject
friend: An Entity
Consider the record structure (following the conventions stated above):
Record structure
(Entity #4434 #547 #666 (#3201 #5588) #555)
where the anchors pointed to are as follows:
#4434 = French1.self (i.e. the anchor in the self slot of the unit named "French1")
#547 = Entity17.self
#666 = Foo.bletch
#3201 = some unlabelled anchor
#5588 = Humanities.requirement
#555 = an unlabelled anchor which would print as: A Programmer
This would correspond to the description form:
An Entity with
primaryAnchor = Handle #4434
relatedEntity = Entity17
funnyField = LISP #666
identifiedAnchors = Currently({Handle #3201, Handle #5588})
friend = A Programmer
Things to note:
1. This description form could not be typed in (or out) since it has Handle descriptors, which can only be generated internally, since they have direct pointers to data structures.
2. Even though the record seems like a uniform list of handles, they are treated quite differently depending on the declarations.
3. The slot (primaryAnchor) declared as a HandleField remains a handle -- i.e. the description is describing the thing which is that anchor. This is also true for the elements of the sequence in identifiedAnchors
4. In this case, this description (which would be generated in running the interpreter) is of an entity which stands for the course French1, and which is also described in anchor #3201 and as the requirements slot for the Humanities unit. (This all depends on knowing what "primaryAnchor", "identifiedAnchors" etc. are intended to mean, but the above interpretation is plausible).
5. The slot (relatedEntity) declared as a CoreferenceField treats the anchor as the destination of the coreference. In this case, Entity17 is another entity being described (through use of a Unit) by the interpreter.
6. The slot (primaryAnchor) declared as a LispField treats it as a lisp object (i.e. a datatype). In fact, the syntax as specified in the descriptor form would not work, since LISP would treat this as the atom #666, not as the data structure. As mentioned above, structures with data types and handles in them cannot be printed directly.
7. The slot (friend) declared as an AnchorField treats it as the anchor belonging to the filler of the fillerpair.
8. If you understand all of this, you have mastered the KRS layers and levels, and a good part of the implementation data structures.