Switsch Statement like in java.

Matej Košík kosik at fiit.stuba.sk
Fri Sep 16 10:31:24 UTC 2005


Hilaire Fernandes wrote:
> Hello,
> 
> In the book "Squeak by examples" 
> (http://www.iam.unibe.ch/~ducasse/FreeBooks.html) , there is a chapter 
> dedicated to procedural to OO programming
> http://www.iam.unibe.ch/~ducasse/FreeBooks/ByExample/30%20-%20Chapter%2028%20-%20Eliminating%20Procedural.pdf 

I have added a note distributed TODO list:
http://altair.dcs.elf.stuba.sk/wiki/Kosik/COND#PossibleEnhancements

Currently, there are only two cond:cond:... invocation in the project where I am using it. Both are 
in the same (horrible-but-now-I-do-not-know-how-to-make-it-prettier-but-now-it-really-does-not-matter)
method. Its source code is:
---------------------------------------------------------------------
createFieldFrom: aSystem
	"The purpose of this method is explained in its sender."

	"This method works in following phases
	1. We go through all the objects living in the system (activated as well as passive).
		1. We make copy of their mailbox to which they are listening.
		2. We add newly created copy to this virtual-machine-state-copy.
		3. We add an association mapping the original mailbox/mail/slit to their corresponding
		    copies. These associations are held by the `mapping' dictionary. This dictionary
		    is a return value of this method. It is used in the second phase of the
		    virtual-machine-state-copying-procedure.
		4. All the futures (THEY CANNOT BE PRESENTS, i.e. no object could listen to them),
		    to which particular mails refer, are collected in a `futures' set for
		    further processing. These should be also processed.
	2. We go through the `futures' collection (we copy it) unless it was already copied
	    (IT SHOULD NOT). This is a recursive procedure which removes the first future
	    from the `futures' collection copies all its elements and
	    1. updates the `mapping' dictionary
	    2. updates the `futures' set
	    and so on until the `futures' set is empty (all the futures in the system were already
	    copied and registered in the `mapping' dictionary).
           We go through the set of all futures again and add a left caption to them indicating
           their id.
	3. We go through the set of all objects again and update the left captions of all the
	    MailboxCopy-ies to catch the information about
           which present mailbox belongs to what kind of object
             - prototype
             - integer
             - copy of a prototype
             That is, we try to conceive reasonable name for all present mailboxes.
        5. We go through the set of all attributes of all object and update the left caption of all the
            MailboxCopy-ies to catch the information about:
            which attribute of what object refers to what mailbox. Here we use those reasonable
	     names of the objects we have conceived in the previous (3-rd) phase.
	     Here we also do the same for the indexed-attributes of particular objects."

	| mapping futures alreadyProcessedFutures |
	mapping _ Dictionary new.
	futures _ Set new.
	alreadyProcessedFutures _ Set new.

	"1-st phase ..."
	aSystem objects do:
		[:object |
			| mailbox mailboxCopy |
			mailbox _ object mailbox.
			mailboxCopy _ MailboxCopy
				id: mailbox id
				forcedRenderingOfPreviousStateOfAnAttributeSetToDifferentValue: mailbox 
forcedRenderingOfPreviousStateOfAnAttributeSetToDifferentValue
				forcedRenderingOfCurrentStateDuringPrimitiveOperation: mailbox 
forcedRenderingOfCurrentStateDuringPrimitiveOperation
				forcedRenderingOfNextStateAfterPrimitiveOperation: mailbox 
forcedRenderingOfNextStateAfterPrimitiveOperation
				isPresent: true.
			mailboxCopies add: mailboxCopy.
			mapping at: mailbox put: mailboxCopy.
			mailbox items do:
				[:mailboxItem |
					mailboxItem
						mailboxCopy: mailboxCopy
						mapping: mapping
						futures: futures
						alreadyProcessedFutures: alreadyProcessedFutures
				]
		].

	"2-nd phase ..."
	[futures isEmpty]
		whileFalse:
			[
				| future futureMailboxCopy |
				future _ futures anyOne.
				futures remove: future.
				alreadyProcessedFutures add: future.
				futureMailboxCopy _ MailboxCopy
					id: future id
					forcedRenderingOfPreviousStateOfAnAttributeSetToDifferentValue: future 
forcedRenderingOfPreviousStateOfAnAttributeSetToDifferentValue
					forcedRenderingOfCurrentStateDuringPrimitiveOperation: future 
forcedRenderingOfCurrentStateDuringPrimitiveOperation
					forcedRenderingOfNextStateAfterPrimitiveOperation: future 
forcedRenderingOfNextStateAfterPrimitiveOperation
					isPresent: false.
				futureMailboxCopy addLeftCaption: future id asString.
				mailboxCopies add: futureMailboxCopy.
				mapping at: future put: futureMailboxCopy.
				future items do:
					[:mailboxItem |
						mailboxItem
							mailboxCopy: futureMailboxCopy
							mapping: mapping
							futures: futures
							alreadyProcessedFutures: alreadyProcessedFutures
					]
			].

	"3-rd phase ..."
	aSystem objects do:
		[:object |
			"Is a given object a prototype? That, is it registered in the `actorTraits'?
			NOTE: `associations' is a sub-dictionary of the `aSystem actorTraits named...'."

			| mailboxCopy associations methodParentSlots |
			mailboxCopy _ mapping at: object mailbox.
			associations _ aSystem actorTraits namedAttributeSlots select:
				[:association | association value listener == object].

			methodParentSlots _ object methodParentSlots.

			[1 <= associations size] ->
				[
					"Current object is registered in `objectTraits' at least once.
					Normally, it is registered there only once, but this branch handles also
					the situation when it is registered therein multiple times."

					associations associations do:
						[:association |
							| prototypeName mailbox |
							prototypeName _ association key.
							mailbox _ association value.
							[object == mailbox listener] assert.
							mailboxCopy addLeftCaption: prototypeName.
						]
				]

			"No. Current object is not a prototype. We will have to determine its
			``name'' in some different way."

			"Is the current object `objectTraits'? This is special situation.
			It has no method parents but it is an important object because
			it has lot of attributes and thus this object should have proper
			name so when it appears in those mailboxes which are attributes
			of this object, it is clear which object refers them."

			cond: [object == aSystem actorTraits] ->
				[
					"Yes. Current object is `actorTraits'"

					mailboxCopy addLeftCaption: 'actorTraits'
				]

			"Does a given object have no method parent?"
			cond: [methodParentSlots size = 0] ->
				[
					"Yes. Current object has no method parents.
					This is unusual, but theoretically it may happen.
					Also `actorTraits' has no method parents, although
					it is usually not sent a message directly."

					mailboxCopy addLeftCaption: '?:', object mailbox id asString
				]

			"Does a given object have only one method parent?"
			 cond: [methodParentSlots size = 1] ->
				[
						"Yes. Current object has only one method parent. This is
						normal situation."

						| methodParentName |
						methodParentName _ methodParentSlots keys anyOne.

						"Is current object an integer?"
						[object isKindOf: IntegerActor] ->
							[
								mailboxCopy addLeftCaption: '#', object value asString, ':', object mailbox id asString
							]

						"Is it a context?"
						cond: [object isKindOf: ContextActor] ->
							[
								mailboxCopy addLeftCaption: object formalBlockAcceptor printStringAsLine, ':', object 
mailbox id asString
							]

						"Is current object copy of the Workspace prototype?"
						cond: [methodParentName = 'actorTraitsOfWorkspace'] ->
							[
								mailboxCopy addLeftCaption: 'workspace:'
							]

						cond: [methodParentName = 'actorTraitsOfMagnitude'] ->
							[
								mailboxCopy addLeftCaption: 'magnitudeTraits:'
							]

						cond: [methodParentName = 'actorTraitsOfNumber'] ->
							[
								mailboxCopy addLeftCaption: 'numberTraits:'
							]

						cond: [methodParentName = 'actorTraitsOfPoint'] ->
							[
								mailboxCopy addLeftCaption: 'pointTraits:'
							]

						cond: [methodParentName = 'actorTraitsOfMatrix'] ->
							[
								mailboxCopy addLeftCaption: 'matrixTraits:'
							]

						cond: [methodParentName = 'actorTraitsOfContext'] ->
							[
								mailboxCopy addLeftCaption: 'contextTraits:'
							]

						cond: [methodParentName endsWith: 'Traits'] ->
							[
								"We have an object, which is not of any destinct identity.
								Its name will be based upon the name of its method parent."

								"... remove the `Traits' suffix"
								mailboxCopy addLeftCaption: (methodParentName truncateTo: methodParentName size - 6), ':', 
object mailbox id asString
							]

						otherwise:
							[
								"This branch handles all the rest cases."
								mailboxCopy addLeftCaption: '?:', object mailbox id asString
							]
				]
			cond: [(methodParentSlots includesKey: 'magnitudeTraits') &
				    (methodParentSlots includesKey: 'numberTraits')] ->
				[
					mailboxCopy addLeftCaption: 'integerTraits:'
				]
			otherwise:
				[
					"Current object has more than one method parent."
					mailboxCopy addLeftCaption: '?:', object mailbox id asString
				]
		].

	"5-th phase ..."

	"NOTE: We have simplified things, we disregard the attributes inherited from attribute
	parents. Those cases are not be visualizable (for now)."
	aSystem objects do:
		[:object |
			| objectCaption |
			
			"Artificially computed name for the currently processed object we have computed
			in the previous phases."
			objectCaption _ (mapping at: object mailbox) leftCaptions first.

			"Here we deal with named attributes."
			object namedAttributeSlots keysAndValuesDo:
				[:key :value |
					"key ... name of the attribute
					 value ... the named attribute itself (a mailbox)"

					(mapping at: value) addLeftCaption: objectCaption, '/', key
				].

			"Here we deal with indexed attributes."
			object indexedAttributeSlots withIndexDo:
				[:value :index |
					"index ... current index of the indexed attribute
					 value ... the indexed attribute itself (a mailbox)"
					(mapping at: value) addLeftCaption: objectCaption, '/', index asString
				]
		].

	^ mapping
---------------------------------------------------------------------
Its purpose is to create a copy of my virtual machine state for later visualization. Those horrible 
cond:cond:cond:...otherwise: decide what caption should be attached to particular mailbox in order 
to give me some useful iniformation.

As for example here
http://altair.dcs.elf.stuba.sk/~kosik/tmp/Book4/page8.html

(I am sorry, the picture is actually scrolled and simple-minded conversion a BookMorph to HTML does 
is in these cases useless)

The captions

"Workspace actorTraits/Workspace" ... I am a (present) mailbox to which `Workspace' object is 
listening.  I am also the mailbox refered by actorTraits's Workspace slit.

"#1:48" ... I am a (present) mailbox to which 1-integer actor is listening. Unique id of this 
mailbox (each to enable me to totally identify them when they are visualized) is 48.

"46" ... I am a (future) mailbox whose id is 46

"55" ... I am a (future) mailbox whose id is 55

"62" ... I am a (future) mailbox whose id is 62

are descriptive which couldn't be generated solely by nice polymorphism technique because what 
should be done (what label should be attached to the particular mailbox) cannot be decided solely by 
the type.

So, there is a single place where I officially use COND. It helps me to solve this ugly problem.

> 
> 
> It is worth reading.

I'll do that. The Visitor pattern suggested earlier was also quite interesting.

> 
> Hilaire Fernandes
> 
> Lic. Edgar J. De Cleene a écrit :
> 
>> Michaël Piel puso en su mail :
>>
>>
>>> Instead of #caseOf: and #caseOf:otherwise: use a dictionary.
>>>
>>> michael
>>
>>
>> Could send to list a few lines example ?
>> I used #caseOf: and #caseOf:otherwise until Matej send about COND.
>> Likes learn more.
>>
>> Edgar
>>
>>
>>
>>     
>>
>>     
>>        
>> ___________________________________________________________ 1GB 
>> gratis, Antivirus y Antispam Correo Yahoo!, el mejor correo web del 
>> mundo http://correo.yahoo.com.ar
>>
> 
> 

Regards
-- 
Matej Košík, ICQ: 300133844, http://altair.dcs.elf.stuba.sk/wiki/Kosik/Main



More information about the Squeak-dev mailing list