Difference between revisions of "Peer-nodal.as"

From Organic Design wiki
(introduce NEXT, PREV, DATA constants)
(legacy)
 
(34 intermediate revisions by 2 users not shown)
Line 1: Line 1:
// NODAL ASSOCIATIONS
+
{{legacy}}
 +
<as>
 +
// Liscenced under LGPL: www.gnu.org/copyleft/lesser.html
 +
//
 +
// peer-nodal.as - ecma-script implementation of the nodal core
 +
// Nad - 2006
 +
//
 +
 
 +
// ISSUES
 
// - associations (maintained class:instance relationships)
 
// - associations (maintained class:instance relationships)
//   instance.create/delete(class) calls class.create/delete(instance)
+
// - get should use class content as default - resolve() doesn't
//  create inserts the instance into the classes instance-loop (list-aspect, next/prev)
+
//  so either add get/set which use resolve, or remove object-freedom and have only .data
//  ie. our list of current children (that our E divides amongst) is also our instance-loop
 
//      has or is are one, they're all just relationships that receive a portion of energy
 
//  laster: a chain of delegate classes is created between root and the instance
 
// - the class of any assoc requires a portion of the quanta
 
//  remember, next/prev and complimented by parent/current (parent is also class)
 
// - this allows alternate quanta be divided between parent and current, thus providing
 
//  energy for the class->instance relationship
 
// - get retreives from class value if no instance value at each step of a path
 
  
// REDUCTION
+
// NODAL PROPERTIES & CORE NODAL CONCEPTS
// - all instance-loops work by going cd this.current then assigning this.current.next to it
+
// - all-capital-identifiers are node-references
//   when a function executes, it can update the loop at that location (equiv to array.push)
+
// - ROOT.idcount is a accumulating-only counter for locally-unique-id number
// - a functions parameters (and even further methods and tools) are child associations
+
// - ROOT.nodes is the current number of instantiated node objects
//   the structures necessary to build the fucntion are child assocs too
+
ROOT = { idcount: 0, nodes: 0 };
 +
VOID = ROOT;
 +
INIT = new node( ROOT ); // Default method executed if quanta sent to empty/new association
 +
NEXT = new node( ROOT );
 +
PREV = new node( ROOT );
 +
FUNC = new node( ROOT );
 +
FOCUS = new node( ROOT );
  
// DATA STRUCTURE
+
// NODE OBJECT
// A question that keeps cropping up is:
+
// - note: only a node's parent can adjust a nodes prev/next
//  is it best to use the language's native list type,
+
function node( key ) {
//  or to use a linked list constructed of ''next'' and ''prev'' refs.
+
ROOT.nodes++;
// The best idea (since swf failed key-as-ref) is to use array-index-only as key,
+
this.id = ROOT.idcount++;
// but allow any datatype as value, that way we can use a list or not later on
+
this.set( [FOCUS], key.get( [INIT] ) );
// values could be node-ref (index), list, lambda, or function-ref
+
}
  
 +
// NODAL METHODS
 +
// - the delete-list is only needed for limited list-space env
 +
// - Actionscript failed ref-as-hashkey test,
 +
//  so we use a id (locally unique identifier) as a lookup-key
 +
// - no delete currently
 +
// - just get/set properties with normal object-accessor way
 +
// - but keep all hierarchy nodal
  
// We'll fake a list-space with an array
+
node.prototype.set = function( path, value ) {
// - create and delete are called internally from get/set
+
var ptr = this._resolve( path );
 +
ptr.value = value;
 +
};
  
PREV = 0;
+
node.prototype.get = function( path ) {
NEXT = 1;
+
var ptr = this._resolve( path );
DATA = 2
+
// need to return class.value onNonExistent
 +
return ptr.value;
 +
};
  
nodal = {};
+
// Resolve creates if non existent and returns reference to result
nodal.root = [];
+
// - this is private, used by get/set
nodal.free = [];
+
node.prototype._resolve = function( path ) {
 +
var context = this;
 +
while( path.length ) {
 +
var key = path.shift();
 +
context = context[key.id] == null ? context[key.id] = new node( key ) : context[ key.id ];
 +
}
 +
return context;
 +
};
  
nodal.create = function() {
+
// Consume one quanta
return this.free.pop();
+
// - each quantum is actually two, one for local instance, one for global class
};
+
// - all instance-loops work by going cd this.current then assigning this.current.next to it
 +
//  when a function executes, it can update the loop at that location (equiv to array.push)
 +
// - a functions parameters (and even further methods and tools) are child associations
 +
//  the structures necessary to build the fucntion are child assocs too
 +
node.prototype.reduce = function() {
 +
 
 +
// Rotate this level's queue
 +
var ptr = this.get( [FOCUS] );
 +
this.set( [FOCUS], this.get( [FOCUS,NEXT] ) );
  
nodal.delete = function( node ) {
+
// If there's a local function declaration, execute
free.push( node );
+
var ref = ptr.get( [FUNC] );
};
+
if ( ref != VOID ) {
 +
ref = ref.call( ptr );
 +
if ( ref == VOID ) {
 +
// Remove focus from loop
 +
ptr.set( [NEXT,PREV], ptr.get( [PREV] ) ); // ptr.next.prev = ptr.prev
 +
ptr.set( [PREV,NEXT], ptr.get( [NEXT] ) ); // ptr.prev.next = ptr.next
 +
}
 +
else if ( ref != ptr ) {
 +
// Replace current ptr with result-ref
 +
ref.set( [NEXT], ptr.get( [NEXT] ) ); // ref.next = ptr.next
 +
ref.set( [PREV], ptr.get( [PREV] ) ); // ref.prev = ptr.prev
 +
ptr.set( [NEXT,PREV], ref ); // ptr.next.prev = ref
 +
ptr.set( [PREV,NEXT], ref ); // ptr.prev.next = ref
 +
}
  
// Actionscript failed ref-as-hashkey test
+
// also call class.reduce()
// - so we need to make wrapper functions that accept/return refs, their form is private
 
// - traverse deals with the NEXT and PREV keys only
 
nodal.traverse = function( path ) {
 
ptr = this;
 
for ( i in path ) ptr = ptr['i'+i];
 
return ptr;
 
}
 
  
// fetch/store deal only with the DATA key
 
nodal.store = function( val ) {
 
this[DATA] = val;
 
 
}
 
}
  
nodal.fetch = function() {
+
// if not, send the quanta downstairs if there's anything in its loop
return this[DATA];
+
else if ( ptr = ptr.get( [FOCUS] ) != VOID ) ptr.reduce();
}
 
  
// This is the old ecma reduction tree taken from SIC code
+
};
// - needs major modification, but has the core language features needed
+
</as>
nodal.reduce = function() {
+
[[Category:ActionScript]]
cwd = root;
 
for (var i = 1; i == 1;) {
 
var queue = cwd.queue;
 
if (queue.length > 0) {
 
var todo = queue.shift();
 
if (next = typeOf(todo) == 'function' ? (i = todo.call) : (cwd = todo)) queue.push(next);
 
}
 
else i = 0;
 
}
 
}
 

Latest revision as of 23:43, 24 September 2013

Legacy.svg Legacy: This article describes a concept that has been superseded in the course of ongoing development on the Organic Design wiki. Please do not develop this any further or base work on this concept, this is only useful for a historic record of work done. You may find a link to the currently used concept or function in this article, if not you can contact the author to find out what has taken the place of this legacy item.

<as> // Liscenced under LGPL: www.gnu.org/copyleft/lesser.html // // peer-nodal.as - ecma-script implementation of the nodal core // Nad - 2006 //

// ISSUES // - associations (maintained class:instance relationships) // - get should use class content as default - resolve() doesn't // so either add get/set which use resolve, or remove object-freedom and have only .data

// NODAL PROPERTIES & CORE NODAL CONCEPTS // - all-capital-identifiers are node-references // - ROOT.idcount is a accumulating-only counter for locally-unique-id number // - ROOT.nodes is the current number of instantiated node objects ROOT = { idcount: 0, nodes: 0 }; VOID = ROOT; INIT = new node( ROOT ); // Default method executed if quanta sent to empty/new association NEXT = new node( ROOT ); PREV = new node( ROOT ); FUNC = new node( ROOT ); FOCUS = new node( ROOT );

// NODE OBJECT // - note: only a node's parent can adjust a nodes prev/next function node( key ) { ROOT.nodes++; this.id = ROOT.idcount++; this.set( [FOCUS], key.get( [INIT] ) ); }

// NODAL METHODS // - the delete-list is only needed for limited list-space env // - Actionscript failed ref-as-hashkey test, // so we use a id (locally unique identifier) as a lookup-key // - no delete currently // - just get/set properties with normal object-accessor way // - but keep all hierarchy nodal

node.prototype.set = function( path, value ) { var ptr = this._resolve( path ); ptr.value = value; };

node.prototype.get = function( path ) { var ptr = this._resolve( path ); // need to return class.value onNonExistent return ptr.value; };

// Resolve creates if non existent and returns reference to result // - this is private, used by get/set node.prototype._resolve = function( path ) { var context = this; while( path.length ) { var key = path.shift(); context = context[key.id] == null ? context[key.id] = new node( key ) : context[ key.id ]; } return context; };

// Consume one quanta // - each quantum is actually two, one for local instance, one for global class // - all instance-loops work by going cd this.current then assigning this.current.next to it // when a function executes, it can update the loop at that location (equiv to array.push) // - a functions parameters (and even further methods and tools) are child associations // the structures necessary to build the fucntion are child assocs too node.prototype.reduce = function() {

// Rotate this level's queue var ptr = this.get( [FOCUS] ); this.set( [FOCUS], this.get( [FOCUS,NEXT] ) );

// If there's a local function declaration, execute var ref = ptr.get( [FUNC] ); if ( ref != VOID ) { ref = ref.call( ptr ); if ( ref == VOID ) { // Remove focus from loop ptr.set( [NEXT,PREV], ptr.get( [PREV] ) ); // ptr.next.prev = ptr.prev ptr.set( [PREV,NEXT], ptr.get( [NEXT] ) ); // ptr.prev.next = ptr.next } else if ( ref != ptr ) { // Replace current ptr with result-ref ref.set( [NEXT], ptr.get( [NEXT] ) ); // ref.next = ptr.next ref.set( [PREV], ptr.get( [PREV] ) ); // ref.prev = ptr.prev ptr.set( [NEXT,PREV], ref ); // ptr.next.prev = ref ptr.set( [PREV,NEXT], ref ); // ptr.prev.next = ref }

// also call class.reduce()

}

// if not, send the quanta downstairs if there's anything in its loop else if ( ptr = ptr.get( [FOCUS] ) != VOID ) ptr.reduce();

}; </as>