SmaCC__SmaCCNode.st
author Jan Vrany <jan.vrany@fit.cvut.cz>
Wed, 07 Dec 2016 13:18:16 +0000
changeset 26 b2c091b8cea1
parent 15 8b8cd1701c33
permissions -rw-r--r--
Fixed initialization of SmaCCEdge There's no `UnicodeString` anymore. Changed: WriteStream on: UnicodeString new to: String new writeStream
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
1
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     1
"{ Package: 'stx:goodies/smaCC' }"
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     2
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     3
"{ NameSpace: SmaCC }"
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     4
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     5
Object subclass:#SmaCCNode
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     6
	instanceVariableNames:'transitions action id'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     7
	classVariableNames:'NextId'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     8
	poolDictionaries:''
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
     9
	category:'SmaCC-Scanner Generator'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    10
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    11
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    12
SmaCCNode comment:'SmaCCNode is a node in a directed graph.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    13
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    14
Instance Variables:
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    15
	action	<SequenceableCollection>	a collection of integers or a symbol. This contains the action to be performed when we match and can''t find a longer match.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    16
	id	<Integer>	a unique number that allows us to sort the nodes
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    17
	transitions	<Collection of: SmaCCEdge>	our transitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    18
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    19
'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    20
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    21
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    22
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    23
!SmaCCNode class methodsFor:'instance creation'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    24
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    25
new
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    26
	^(super new)
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    27
		initialize;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    28
		yourself
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    29
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    30
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    31
!SmaCCNode class methodsFor:'class initialization'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    32
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    33
initialize
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    34
	NextId := 0
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    35
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    36
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    37
!SmaCCNode methodsFor:'compiling'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    38
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    39
asStatement: methodMap usingSelectorMap: aDictionary forClass: aClass 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    40
	| stream |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    41
	stream := WriteStream on: (String new: 128).
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    42
	self hasSimpleLoop ifTrue: [stream nextPut: $[].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    43
	self writeMatchingCodeOn: stream usingSelectorMap: aDictionary.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    44
	(self sortedTransitionsFor: aClass) do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    45
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    46
			each to == self 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    47
				ifTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    48
					[stream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    49
						nextPutAll: each expression;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    50
						nextPut: $];
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    51
						nextPutAll: ' whileTrue.';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    52
						cr]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    53
				ifFalse: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    54
					[stream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    55
						nextPutAll: each expression;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    56
						nextPutAll: ' ifTrue: ['.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    57
					stream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    58
						nextPutAll: (methodMap at: each to
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    59
									ifAbsentPut: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    60
										[each to 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    61
											asStatement: methodMap
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    62
											usingSelectorMap: aDictionary
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    63
											forClass: aClass]);
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    64
						nextPutAll: '].';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    65
						cr]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    66
	(transitions notEmpty or: [action isNil]) 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    67
		ifTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    68
			[stream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    69
				nextPutAll: '^self reportLastMatch';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    70
				cr].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    71
	^stream contents
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    72
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    73
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    74
compileInto: aClass usingSelectorMap: aDictionary 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    75
	| methodNodes methodMap index |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    76
	methodNodes := self statesToMakeIntoMethods.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    77
	methodMap := self methodNameMapFor: methodNodes.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    78
	index := 0.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    79
	methodNodes do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    80
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    81
			| stream |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    82
			stream := WriteStream on: (String new: 1000).
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    83
			stream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    84
				nextPutAll: (each == self 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    85
							ifTrue: ['scanForToken']
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    86
							ifFalse: ['scan' , (index := index + 1) printString]);
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    87
				cr.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    88
			stream nextPutAll: (each 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    89
						asStatement: methodMap
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    90
						usingSelectorMap: aDictionary
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    91
						forClass: aClass).
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    92
			aClass 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    93
				compile: (self optimizedParseTreeFor: stream contents) formattedCode
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    94
				classified: #'generated-scanner']
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    95
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    96
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    97
methodNameMapFor: methodNodes 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    98
	| index methodMap |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
    99
	methodMap := IdentityDictionary new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   100
	index := 0.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   101
	methodNodes do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   102
			[:value | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   103
			methodMap at: value
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   104
				put: (value == self 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   105
						ifTrue: ['^self scanForToken']
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   106
						ifFalse: ['^self scan' , (index := index + 1) printString])].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   107
	^methodMap
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   108
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   109
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   110
needsSeparateMethod
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   111
	^self allStates size > 20
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   112
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   113
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   114
optimizationRewriter
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   115
	| rewriter |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   116
	rewriter := ParseTreeRewriter new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   117
	rewriter
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   118
		replace: 'Core.Character' with: 'Character';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   119
		replace: '`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   120
				[`@.Stmts2.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   121
				currentCharacter ~~ `#l] whileTrue.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   122
				currentCharacter == `#l ifTrue: [`@.Stmts3].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   123
				`@.Stmts4'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   124
			with: '`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   125
				[`@.Stmts2.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   126
				currentCharacter ~~ `#l] whileTrue.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   127
				`@.Stmts3';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   128
		replaceMethod: '`name
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   129
							`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   130
							`@a ifTrue: [`@.Stmts2.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   131
									^self `name].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   132
							`@.Stmts3'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   133
			with: '`name
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   134
				[`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   135
				`@a] whileTrue: [`@.Stmts2].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   136
				`@.Stmts3';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   137
		replace: '`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   138
				currentCharacter isLiteral ifTrue: [`@.Stmts2].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   139
				`@.Stmts3'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   140
			with: '`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   141
				`@.Stmts2';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   142
"		replace: '``@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   143
				(`@a ifTrue: [``@.Stmts2]) `{:node :dictionary | | index myStatements |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   144
						index := node parent statements indexOf: node.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   145
						myStatements := node parent statements.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   146
						dictionary at: #size put: ``@.Stmts2 size - (myStatements size - index).
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   147
						index ~~  myStatements size and: [``@.Stmts2 size >= (myStatements size - index) and: [
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   148
							(index + 1 to: myStatements size) allSatisfy: [:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   149
								(myStatements at: each) = (``@.Stmts2 at: ``@.Stmts2 size - (myStatements size - each))]]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   150
						}.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   151
				``@.Stmts3'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   152
			with: '``@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   153
				`{:dictionary | RBMessageNode receiver: `@a selector: #ifTrue: arguments: (Array with: (RBBlockNode body: (RBSequenceNode statements: (``@.Stmts2 copyFrom: 1 to: (dictionary at: #size)))))}.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   154
				``@.Stmts3';"
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   155
		replace: '`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   156
				`.Stmt.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   157
				`@.Stmts.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   158
				`@a ifTrue: [self step. `.Stmt. `@.Stmts].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   159
				`@.Stmts2'
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   160
			with: '`@.Stmts1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   161
				`@a ifTrue: [self step].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   162
				`.Stmt.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   163
				`@.Stmts.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   164
				`@.Stmts2'.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   165
	^rewriter
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   166
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   167
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   168
optimizedParseTreeFor: aString 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   169
	| tree rewriter |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   170
	tree := RBParser parseMethod: aString.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   171
	rewriter := self optimizationRewriter.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   172
	[rewriter executeTree: tree] whileTrue: [tree := rewriter tree].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   173
	^tree
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   174
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   175
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   176
sortedTransitionsFor: aClass
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   177
	| frequencies |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   178
	frequencies := (aClass realClass ifNil: [SmaCCScanner]) frequencyTable.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   179
	^transitions asSortedCollection: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   180
			[:a :b | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   181
			| aFrequency bFrequency |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   182
			aFrequency := a characters inject: 0
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   183
						into: [:sum :each | sum + (frequencies at: each asInteger \\ frequencies size + 1)].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   184
			bFrequency := b characters inject: 0
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   185
						into: [:sum :each | sum + (frequencies at: each asInteger \\ frequencies size + 1)].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   186
			aFrequency > bFrequency 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   187
				or: [aFrequency = bFrequency and: [a characters first < b characters first]]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   188
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   189
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   190
statesToMakeIntoMethods
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   191
	| allStates incoming |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   192
	allStates := self allStates.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   193
	incoming := Dictionary new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   194
	allStates do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   195
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   196
			each transitions do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   197
					[:edge | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   198
					each ~~ edge to 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   199
						ifTrue: [(incoming at: edge to ifAbsentPut: [Set new]) add: each]]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   200
	^(allStates asOrderedCollection select: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   201
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   202
			self == each or: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   203
					[each isTerminalNode not and: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   204
							[(incoming at: each ifAbsent: [#()]) size > 1 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   205
								or: [each needsSeparateMethod]]]]) 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   206
		asSortedCollection: [:a :b | a id < b id]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   207
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   208
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   209
writeMatchingCodeOn: aStream usingSelectorMap: aDictionary 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   210
	| matchedItem |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   211
	action size > 0 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   212
		ifTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   213
			[matchedItem := aDictionary at: action first ifAbsent: [action asArray].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   214
			aStream nextPutAll: (transitions isEmpty 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   215
						ifTrue: ['^self recordAndReportMatch:']
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   216
						ifFalse: ['self recordMatch: ']).
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   217
			matchedItem isSymbol 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   218
				ifTrue: [aStream nextPutAll: matchedItem storeString]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   219
				ifFalse: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   220
					[aStream nextPutAll: '#('.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   221
					matchedItem do: [:each | aStream nextPutAll: each storeString]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   222
						separatedBy: [aStream nextPut: $ ].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   223
					aStream nextPut: $)].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   224
			aStream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   225
				nextPut: $.;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   226
				cr].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   227
	transitions notEmpty 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   228
		ifTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   229
			[aStream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   230
				nextPutAll: 'self step.';
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   231
				cr]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   232
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   233
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   234
!SmaCCNode methodsFor:'converting'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   235
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   236
asDFA
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   237
	self asDFA: IdentitySet new merged: Dictionary new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   238
	self removeDuplicateNodes.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   239
	^self
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   240
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   241
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   242
!SmaCCNode methodsFor:'edges'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   243
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   244
addEdgeTo: endNode 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   245
	transitions add: (SmaCCEdge to: endNode on: nil)
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   246
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   247
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   248
addEdgeTo: endNode on: characterCollection 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   249
	transitions add: (SmaCCEdge to: endNode on: characterCollection)
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   250
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   251
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   252
!SmaCCNode methodsFor:'initialize-release'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   253
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   254
action: anObject 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   255
	anObject isNil ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   256
	action := anObject isSymbol 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   257
				ifTrue: [anObject]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   258
				ifFalse: [SortedCollection with: anObject]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   259
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   260
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   261
initialize
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   262
	id := NextId := NextId + 1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   263
	transitions := SortedCollection new
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   264
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   265
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   266
!SmaCCNode methodsFor:'printing'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   267
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   268
printOn: aStream 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   269
	aStream
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   270
		nextPutAll: self class name;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   271
		nextPut: $(;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   272
		nextPutAll: id printString;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   273
		nextPut: $)
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   274
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   275
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   276
!SmaCCNode methodsFor:'private'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   277
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   278
action
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   279
	^action
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   280
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   281
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   282
addActions: aCollection 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   283
	aCollection isNil ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   284
	action isNil 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   285
		ifTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   286
			[action := aCollection copy.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   287
			^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   288
	action isSymbol ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   289
	aCollection isSymbol ifTrue: [^action := aCollection].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   290
	aCollection 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   291
		do: [:each | (action includes: each) ifFalse: [action add: each]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   292
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   293
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   294
allCharacterTransitions: aSet into: aNode 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   295
	| index each |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   296
	(aSet includes: self) ifTrue: [^#()].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   297
	aSet add: self.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   298
	aNode addActions: action.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   299
	index := 1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   300
	[index <= transitions size] whileTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   301
			[each := transitions at: index.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   302
			index := index + 1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   303
			each isEpsilonTransition 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   304
				ifTrue: [each to allCharacterTransitions: aSet into: aNode]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   305
				ifFalse: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   306
					[(aNode transitions includes: each) ifFalse: [aNode transitions add: each]]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   307
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   308
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   309
allCharacterTransitionsAndActionsInto: aNode 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   310
	| seen |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   311
	seen := IdentitySet new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   312
	self allCharacterTransitions: seen into: aNode
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   313
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   314
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   315
allStates
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   316
	| nodes |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   317
	nodes := Set new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   318
	self allStatesInto: nodes.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   319
	^nodes
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   320
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   321
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   322
allStatesInto: aSet 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   323
	(aSet includes: self) ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   324
	aSet add: self.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   325
	transitions do: [:each | each to allStatesInto: aSet]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   326
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   327
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   328
asDFA: aSet merged: aDictionary 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   329
	| newTransitions |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   330
	(aSet includes: self) ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   331
	aSet add: self.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   332
	newTransitions := OrderedCollection new: transitions size.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   333
	transitions do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   334
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   335
			| existingEdges new |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   336
			new := each copy.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   337
			existingEdges := newTransitions select: [:edge | edge conflictsWith: each].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   338
			existingEdges do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   339
					[:existing | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   340
					| node newChars existingChars chars |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   341
					node := aDictionary 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   342
								at: (SortedCollection with: existing to id with: new to id) asArray
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   343
								ifAbsentPut: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   344
									[node := self class new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   345
									node transitions: ((Set 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   346
												withAll: (existing to transitions collect: [:edge | edge copy]))
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   347
												addAll: (new to transitions collect: [:edge | edge copy]);
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   348
												yourself).
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   349
									node mergeCharacterTransitions.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   350
									node addActions: existing to action.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   351
									node addActions: new to action.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   352
									node].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   353
					newChars := new characters.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   354
					chars := newChars select: [:char | existing includesCharacter: char].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   355
					chars notEmpty 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   356
						ifTrue: [newTransitions addFirst: (SmaCCEdge to: node on: chars)].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   357
					existingChars := existing characters.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   358
					existing removeCharacters: newChars.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   359
					new removeCharacters: existingChars.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   360
					existing isEmpty ifTrue: [newTransitions remove: existing]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   361
			new isEmpty ifFalse: [newTransitions add: new]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   362
	transitions := newTransitions.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   363
	transitions do: [:each | each to asDFA: aSet merged: aDictionary]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   364
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   365
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   366
asNFAWithoutEpsilonTransitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   367
	| seen node |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   368
	node := self class new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   369
	self allCharacterTransitionsAndActionsInto: node.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   370
	seen := IdentitySet new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   371
	node asNFAWithoutEpsilonTransitions: seen.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   372
	seen := IdentitySet new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   373
	node removeEpsilonTransitions: seen.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   374
	node cleanUp.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   375
	^node
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   376
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   377
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   378
asNFAWithoutEpsilonTransitions: aSet 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   379
	| index each |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   380
	(aSet includes: self) ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   381
	aSet add: self.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   382
	index := 1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   383
	[index <= transitions size] whileTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   384
			[each := transitions at: index.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   385
			index := index + 1.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   386
			each isEpsilonTransition 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   387
				ifTrue: [each to allCharacterTransitionsAndActionsInto: self]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   388
				ifFalse: [each to asNFAWithoutEpsilonTransitions: aSet]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   389
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   390
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   391
cleanUp
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   392
	self removeDuplicateNodes.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   393
	self mergeAllTransitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   394
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   395
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   396
id
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   397
	^id
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   398
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   399
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   400
mergeAllTransitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   401
	| nodes |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   402
	nodes := self allStates.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   403
	nodes do: [:each | each mergeCharacterTransitions]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   404
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   405
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   406
mergeCharacterTransitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   407
	| toMap |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   408
	toMap := IdentityDictionary new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   409
	transitions copy do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   410
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   411
			(toMap includesKey: each to) 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   412
				ifTrue: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   413
					[(toMap at: each to) mergeWith: each.
15
8b8cd1701c33 added version_SVN method
vranyj1
parents: 1
diff changeset
   414
					transitions removeIdentical: (transitions detect:[:e|e = each])
8b8cd1701c33 added version_SVN method
vranyj1
parents: 1
diff changeset
   415
					]
1
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   416
				ifFalse: [toMap at: each to put: each]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   417
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   418
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   419
removeDuplicateEdges
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   420
	transitions := transitions asSet asSortedCollection
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   421
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   422
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   423
removeDuplicateNodes
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   424
	| nodes |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   425
	
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   426
	[nodes := self allStates.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   427
	nodes do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   428
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   429
			each
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   430
				mergeCharacterTransitions;
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   431
				removeDuplicateEdges].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   432
	self removeDuplicateNodes: nodes] 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   433
			whileTrue
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   434
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   435
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   436
removeDuplicateNodes: aCollection 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   437
	| merged nodePartition |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   438
	merged := false.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   439
	nodePartition := Dictionary new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   440
	aCollection do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   441
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   442
			(nodePartition at: (Array with: each transitions size with: each action)
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   443
				ifAbsentPut: [OrderedCollection new]) add: each].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   444
	nodePartition do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   445
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   446
			| seen |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   447
			seen := OrderedCollection new.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   448
			each do: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   449
					[:node | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   450
					| existingNode |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   451
					existingNode := seen 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   452
								detect: [:otherNode | otherNode transitionsMatch: node]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   453
								ifNone: [nil].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   454
					existingNode isNil 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   455
						ifTrue: [seen add: node]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   456
						ifFalse: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   457
							[merged := true.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   458
							node oneWayBecome: existingNode]]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   459
	^merged
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   460
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   461
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   462
removeEpsilonTransitions: aSet 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   463
	(aSet includes: self) ifTrue: [^self].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   464
	aSet add: self.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   465
	transitions copy 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   466
		do: [:each | each isEpsilonTransition ifTrue: [transitions remove: each]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   467
	transitions do: [:each | each to removeEpsilonTransitions: aSet]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   468
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   469
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   470
transitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   471
	^transitions
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   472
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   473
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   474
transitions: aCollection 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   475
	transitions := aCollection asSortedCollection
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   476
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   477
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   478
transitionsMatch: aNode 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   479
	^aNode transitions allSatisfy: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   480
			[:each | 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   481
			(transitions includes: each) or: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   482
					[each to = aNode and: 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   483
							[each characters 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   484
								= (transitions detect: [:edge | edge to = self] ifNone: [^false]) 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   485
										characters]]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   486
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   487
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   488
!SmaCCNode methodsFor:'public'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   489
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   490
hasSimpleLoop
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   491
	^transitions anySatisfy: [:each | each to == self]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   492
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   493
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   494
isTerminalNode
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   495
	^transitions isEmpty or: [transitions size = 1 and: [self hasSimpleLoop]]
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   496
!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   497
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   498
simulate: aStream 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   499
	| char |
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   500
	aStream atEnd ifTrue: [^action].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   501
	char := aStream next.
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   502
	transitions 
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   503
		do: [:each | (each characters includes: char) ifTrue: [^each to simulate: aStream]].
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   504
	^action
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   505
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   506
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   507
!SmaCCNode class methodsFor:'documentation'!
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   508
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   509
version
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   510
    ^ '$Header: /opt/data/cvs/stx/goodies/smaCC/SmaCC__SmaCCNode.st,v 1.1 2006-02-09 21:17:46 vranyj1 Exp $'
15
8b8cd1701c33 added version_SVN method
vranyj1
parents: 1
diff changeset
   511
!
8b8cd1701c33 added version_SVN method
vranyj1
parents: 1
diff changeset
   512
8b8cd1701c33 added version_SVN method
vranyj1
parents: 1
diff changeset
   513
version_SVN
8b8cd1701c33 added version_SVN method
vranyj1
parents: 1
diff changeset
   514
    ^ '$Id$'
1
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   515
! !
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   516
b8cca2663544 Initial import
vranyj1
parents:
diff changeset
   517
SmaCCNode initialize!