Surpass

ExcelFormulaLexer.rb

# ExcelFormulaLexer (ExcelFormula.g)
# Generated by ANTLR 3.1.2-2008-10-21 on 2009-06-15 23:03:59

class ExcelFormulaLexer
    require 'stringio'

	COMMA=25
	TRUE_CONST=12
	PERCENT=11
	POWER=10
	FUNC_CHOOSE=33
	BANG=28
	EQ=4
	QUOTENAME=31
	LT=19
	NE=21
	GT=20
	FUNC_IF=32
	RP=27
	FALSE_CONST=13
	LP=26
	GE=23
	MUL=8
	NUM_CONST=16
	REF2D=17
	SEMICOLON=24
	CONCAT=5
	EOF=-1
	LE=22
	INT_CONST=15
	STR_CONST=14
	COLON=18
	DIV=9
	DIGIT=29
	SUB=7
	NAME=30
	ADD=6
	
    def initialize(input)
        input = StringIO.new(input) if input.respond_to?(:to_str)
        @input = CharStream.new(input)
        @backtracking = 0
        @failed = false

    end

    def next_token
    	# TODO: catch exceptions
		@token = nil
		@channel = nil
		@text = nil

		@start = @input.index
		@line = @input.line
		@pos = @input.column

		@type = nil
		@type_int = nil

		return :EOF if @input.look_ahead(1) == :EOF

		match_Tokens()

		if @token == nil
			@text ||= @input.substring(@start, @input.index - 1)
			@token = Token.new(@type, @type_int, @line, @pos, @text, @channel)
		end

        return @token
    end

    class Token
        attr_reader :token_type
        attr_reader :int_type
        attr_reader :line
        attr_reader :pos
        attr_reader :text
        attr_reader :channel

        def initialize(token_type, int_type, line, pos, text, channel = nil)
            @token_type = token_type
            @int_type = int_type
            @line = line
            @pos = pos
            @text = text
            @channel = channel
        end

		alias :to_i :int_type
    end


    private

    class CharStream
        attr_reader :line
        attr_reader :column
        attr_reader :index

        def initialize(input)
            @buffer = ""
            @input = input
            @line = 1
            @column = 0

            @index = 0;
        end

        # returns a Fixnum between 0 and 0xFFFF or :EOF
        def look_ahead(pos)
            offset = @index + pos - 1
            if @buffer.length < offset + 1
                char = @input.read(offset + 1 - @buffer.length)
                @buffer << char if not char.nil?
            end

            if offset < @buffer.length
                @buffer[offset]
            else
                :EOF
            end
        end

        def mark
            @state = { :index => @index, :line => @line, :column => @column }
            return 0
        end

        def rewind(marker)
            @index = @state[:index]
            @line = @state[:line]
            @column = @state[:column]
        end

        def consume
           look_ahead(1) # force a read from the input if necessary
           @column = @column + 1
           if @buffer[@index] == ?\n
                @line = @line + 1
                @column = 0
           end
           @index = @index + 1
        end

        def substring(start, stop)
            @buffer.slice(start, stop - start + 1)
        end
    end


    def match(value = nil)
        @failed = false
        case
            when value.nil?
                @input.consume()
            when value.respond_to?(:to_str)
                catch(:done) do
                    value.each_byte do |c|
                        @failed ||= !(@input.look_ahead(1) == c)
                        @input.consume() if !@failed
                        throw :done if @failed
                    end
                end
            else
                @failed = !(@input.look_ahead(1) == value)
                @input.consume() if !@failed
        end

		if @failed && @backtracking <= 0
			raise "Expected #{value.respond_to?(:chr) ? value.chr : value}"
		end
    end

    def match_range(from, to)
        char = @input.look_ahead(1)

        if char != :EOF && (char >= from || char <= to)
			@failed = false
			match()
        elsif @backtracking > 0
            @failed = true
        else
            raise "Expected [#{from.chr}..#{to.chr}]"
        end
    end

    def match_EQ()

    		# 332:5: '='
    		match(?=)

    end

    def match_LT()

    		@type = :LT
    		@type_int = LT
    		# 333:5: '<'
    		match(?<)
    end

    def match_GT()

    		@type = :GT
    		@type_int = GT
    		# 334:5: '>'
    		match(?>)
    end

    def match_NE()

    		@type = :NE
    		@type_int = NE
    		# 335:5: '<>'
    		match("<>")

    end

    def match_LE()

    		@type = :LE
    		@type_int = LE
    		# 336:5: '<='
    		match("<=")

    end

    def match_GE()

    		@type = :GE
    		@type_int = GE
    		# 337:5: '>='
    		match(">=")

    end

    def match_ADD()

    		@type = :ADD
    		@type_int = ADD
    		# 339:6: '+'
    		match(?+)
    end

    def match_SUB()

    		@type = :SUB
    		@type_int = SUB
    		# 340:6: '-'
    		match(?-)
    end

    def match_MUL()

    		@type = :MUL
    		@type_int = MUL
    		# 341:6: '*'
    		match(?*)
    end

    def match_DIV()

    		@type = :DIV
    		@type_int = DIV
    		# 342:6: '/'
    		match(?/)
    end

    def match_COLON()

    		@type = :COLON
    		@type_int = COLON
    		# 344:8: ':'
    		match(?:)
    end

    def match_SEMICOLON()

    		@type = :SEMICOLON
    		@type_int = SEMICOLON
    		# 345:12: ';'
    		match(?;)
    end

    def match_COMMA()

    		@type = :COMMA
    		@type_int = COMMA
    		# 346:8: ','
    		match(?,)
    end

    def match_LP()

    		@type = :LP
    		@type_int = LP
    		# 348:5: '('
    		match(?()
    end

    def match_RP()

    		@type = :RP
    		@type_int = RP
    		# 349:5: ')'
    		match(?))
    end

    def match_CONCAT()

    		@type = :CONCAT
    		@type_int = CONCAT
    		# 350:9: '&'
    		match(?&)
    end

    def match_PERCENT()

    		@type = :PERCENT
    		@type_int = PERCENT
    		# 351:10: '%'
    		match(?%)
    end

    def match_POWER()

    		@type = :POWER
    		@type_int = POWER
    		# 352:8: '^'
    		match(?^)
    end

    def match_BANG()

    		@type = :BANG
    		@type_int = BANG
    		# 353:7: '!'
    		match(?!)
    end

    def match_DIGIT()

    		@type = :DIGIT
    		@type_int = DIGIT
    		# 355:8: '0' .. '9'
    		match_range(?0, ?9)
    end

    def match_INT_CONST()

    		@type = :INT_CONST
    		@type_int = INT_CONST
    		# 357:12: ( DIGIT )+
    		# 357:12: ( DIGIT )+
    		matchedOnce1 = false
    		while true
    		    alt1 = 2
    		    # 
    		    look_ahead1_0 = @input.look_ahead(1)
    		    look_ahead1_0 = -1 if look_ahead1_0 == :EOF
    		    if (look_ahead1_0 >= ?0 && look_ahead1_0 <= ?9)  
    		        alt1 = 1
    		    end
    		    case alt1
    		        when 1
    		            # 357:12: DIGIT
    		            match_DIGIT()
    		        else
    		            break
    		    end
    		    matchedOnce1 = true
    		end

    		if !matchedOnce1
    		    raise "Expected at least one match: 357:12: ( DIGIT )+"
    		end
    end

    def match_NUM_CONST()

    		@type = :NUM_CONST
    		@type_int = NUM_CONST
    		# 358:12: ( DIGIT )* '.' ( DIGIT )+ ( ( 'E' | 'e' ) ( '+' | '-' )? ( DIGIT )+ )?
    		# 358:12: ( DIGIT )*
    		while true
    		    alt2 = 2
    		    # 
    		    look_ahead2_0 = @input.look_ahead(1)
    		    look_ahead2_0 = -1 if look_ahead2_0 == :EOF
    		    if (look_ahead2_0 >= ?0 && look_ahead2_0 <= ?9)  
    		        alt2 = 1
    		    end
    		    case alt2
    		        when 1
    		            # 358:12: DIGIT
    		            match_DIGIT()
    		        else
    		            break
    		    end
    		end
    		match(?.)
    		# 358:23: ( DIGIT )+
    		matchedOnce3 = false
    		while true
    		    alt3 = 2
    		    # 
    		    look_ahead3_0 = @input.look_ahead(1)
    		    look_ahead3_0 = -1 if look_ahead3_0 == :EOF
    		    if (look_ahead3_0 >= ?0 && look_ahead3_0 <= ?9)  
    		        alt3 = 1
    		    end
    		    case alt3
    		        when 1
    		            # 358:23: DIGIT
    		            match_DIGIT()
    		        else
    		            break
    		    end
    		    matchedOnce3 = true
    		end

    		if !matchedOnce3
    		    raise "Expected at least one match: 358:23: ( DIGIT )+"
    		end
    		# 358:30: ( ( 'E' | 'e' ) ( '+' | '-' )? ( DIGIT )+ )?
    		alt6 = 2
    		# 
    		look_ahead6_0 = @input.look_ahead(1)

    		look_ahead6_0 = -1 if look_ahead6_0 == :EOF
    		if look_ahead6_0 == ?E || look_ahead6_0 == ?e  
    		    alt6 = 1
    		end
    		case alt6
    		    when 1
    		        # 358:31: ( 'E' | 'e' ) ( '+' | '-' )? ( DIGIT )+
    		        if @input.look_ahead(1) == ?E || @input.look_ahead(1) == ?e
    		            match()
    		        else
    		            raise "Expected set"
    		        end
    		        # 358:41: ( '+' | '-' )?
    		        alt4 = 2
    		        # 
    		        look_ahead4_0 = @input.look_ahead(1)

    		        look_ahead4_0 = -1 if look_ahead4_0 == :EOF
    		        if look_ahead4_0 == ?+ || look_ahead4_0 == ?-  
    		            alt4 = 1
    		        end
    		        case alt4
    		            when 1
    		                # 
    		                if @input.look_ahead(1) == ?+ || @input.look_ahead(1) == ?-
    		                    match()
    		                else
    		                    raise "Expected set"
    		                end
    		        end
    		        # 358:52: ( DIGIT )+
    		        matchedOnce5 = false
    		        while true
    		            alt5 = 2
    		            # 
    		            look_ahead5_0 = @input.look_ahead(1)
    		            look_ahead5_0 = -1 if look_ahead5_0 == :EOF
    		            if (look_ahead5_0 >= ?0 && look_ahead5_0 <= ?9)  
    		                alt5 = 1
    		            end
    		            case alt5
    		                when 1
    		                    # 358:52: DIGIT
    		                    match_DIGIT()
    		                else
    		                    break
    		            end
    		            matchedOnce5 = true
    		        end

    		        if !matchedOnce5
    		            raise "Expected at least one match: 358:52: ( DIGIT )+"
    		        end
    		end
    end

    def match_STR_CONST()

    		@type = :STR_CONST
    		@type_int = STR_CONST
    		# 359:12: '\"' ~ '\"' '\"'
    		match(?")
    		if (@input.look_ahead(1) >= 0x0000 && @input.look_ahead(1) <= ?!) || (@input.look_ahead(1) >= ?# && @input.look_ahead(1) <= 0x00FF)
    		    match()
    		else
    		    raise "Expected set"
    		end
    		match(?")
    end

    def match_REF2D()

    		@type = :REF2D
    		@type_int = REF2D
    		# 360:8: ( '$' )? ( 'A' .. 'I' )? ( 'A' .. 'Z' ) ( '$' )? ( DIGIT )+
    		# 360:8: ( '$' )?
    		alt7 = 2
    		# 
    		look_ahead7_0 = @input.look_ahead(1)

    		look_ahead7_0 = -1 if look_ahead7_0 == :EOF
    		if look_ahead7_0 == ?$  
    		    alt7 = 1
    		end
    		case alt7
    		    when 1
    		        # 360:8: '$'
    		        match(?$)
    		end
    		# 360:13: ( 'A' .. 'I' )?
    		alt8 = 2
    		# 
    		look_ahead8_0 = @input.look_ahead(1)

    		look_ahead8_0 = -1 if look_ahead8_0 == :EOF
    		if (look_ahead8_0 >= ?A && look_ahead8_0 <= ?I)  
    		    # 
    		    look_ahead8_1 = @input.look_ahead(2)

    		    look_ahead8_1 = -1 if look_ahead8_1 == :EOF
    		    if (look_ahead8_1 >= ?A && look_ahead8_1 <= ?Z)  
    		        alt8 = 1
    		    end
    		end
    		case alt8
    		    when 1
    		        # 360:14: 'A' .. 'I'
    		        match_range(?A, ?I)
    		end
    		# 360:26: 'A' .. 'Z'
    		match_range(?A, ?Z)
    		# 360:36: ( '$' )?
    		alt9 = 2
    		# 
    		look_ahead9_0 = @input.look_ahead(1)

    		look_ahead9_0 = -1 if look_ahead9_0 == :EOF
    		if look_ahead9_0 == ?$  
    		    alt9 = 1
    		end
    		case alt9
    		    when 1
    		        # 360:36: '$'
    		        match(?$)
    		end
    		# 360:41: ( DIGIT )+
    		matchedOnce10 = false
    		while true
    		    alt10 = 2
    		    # 
    		    look_ahead10_0 = @input.look_ahead(1)
    		    look_ahead10_0 = -1 if look_ahead10_0 == :EOF
    		    if (look_ahead10_0 >= ?0 && look_ahead10_0 <= ?9)  
    		        alt10 = 1
    		    end
    		    case alt10
    		        when 1
    		            # 360:41: DIGIT
    		            match_DIGIT()
    		        else
    		            break
    		    end
    		    matchedOnce10 = true
    		end

    		if !matchedOnce10
    		    raise "Expected at least one match: 360:41: ( DIGIT )+"
    		end
    end

    def match_TRUE_CONST()

    		@type = :TRUE_CONST
    		@type_int = TRUE_CONST
    		# 361:13: ( 'T' | 't' ) ( 'R' | 'r' ) ( 'U' | 'u' ) ( 'E' | 'e' )
    		if @input.look_ahead(1) == ?T || @input.look_ahead(1) == ?t
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?R || @input.look_ahead(1) == ?r
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?U || @input.look_ahead(1) == ?u
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?E || @input.look_ahead(1) == ?e
    		    match()
    		else
    		    raise "Expected set"
    		end
    end

    def match_FALSE_CONST()

    		@type = :FALSE_CONST
    		@type_int = FALSE_CONST
    		# 362:14: ( 'F' | 'f' ) ( 'A' | 'a' ) ( 'L' | 'l' ) ( 'S' | 's' ) ( 'E' | 'e' )
    		if @input.look_ahead(1) == ?F || @input.look_ahead(1) == ?f
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?A || @input.look_ahead(1) == ?a
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?L || @input.look_ahead(1) == ?l
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?S || @input.look_ahead(1) == ?s
    		    match()
    		else
    		    raise "Expected set"
    		end
    		if @input.look_ahead(1) == ?E || @input.look_ahead(1) == ?e
    		    match()
    		else
    		    raise "Expected set"
    		end
    end

    def match_NAME()

    		@type = :NAME
    		@type_int = NAME
    		# 363:7: '\\w[\\.\\w]*'
    		match("w[.w]*")

    end

    def match_QUOTENAME()

    		@type = :QUOTENAME
    		@type_int = QUOTENAME
    		# 364:12: '\\'(?:[^\\']|\\'\\')*\\''
    		match("'(?:[^']|'')*'")

    end

    def match_FUNC_IF()

    		@type = :FUNC_IF
    		@type_int = FUNC_IF
    		# 365:10: 'IF'
    		match("IF")

    end

    def match_FUNC_CHOOSE()

    		@type = :FUNC_CHOOSE
    		@type_int = FUNC_CHOOSE
    		# 366:14: 'CHOOSE'
    		match("CHOOSE")

    end

    def match_Tokens()

    		# 1:8: ( LT | GT | NE | LE | GE | ADD | SUB | MUL | DIV | COLON | SEMICOLON | COMMA | LP | RP | CONCAT | PERCENT | POWER | BANG | DIGIT | INT_CONST | NUM_CONST | STR_CONST | REF2D | TRUE_CONST | FALSE_CONST | NAME | QUOTENAME | FUNC_IF | FUNC_CHOOSE )
    		alt11 = 29
    		alt11 = DFA11.predict(self, @input)
    		case alt11
    		    when 1
    		        # 1:10: LT
    		        match_LT()
    		    when 2
    		        # 1:13: GT
    		        match_GT()
    		    when 3
    		        # 1:16: NE
    		        match_NE()
    		    when 4
    		        # 1:19: LE
    		        match_LE()
    		    when 5
    		        # 1:22: GE
    		        match_GE()
    		    when 6
    		        # 1:25: ADD
    		        match_ADD()
    		    when 7
    		        # 1:29: SUB
    		        match_SUB()
    		    when 8
    		        # 1:33: MUL
    		        match_MUL()
    		    when 9
    		        # 1:37: DIV
    		        match_DIV()
    		    when 10
    		        # 1:41: COLON
    		        match_COLON()
    		    when 11
    		        # 1:47: SEMICOLON
    		        match_SEMICOLON()
    		    when 12
    		        # 1:57: COMMA
    		        match_COMMA()
    		    when 13
    		        # 1:63: LP
    		        match_LP()
    		    when 14
    		        # 1:66: RP
    		        match_RP()
    		    when 15
    		        # 1:69: CONCAT
    		        match_CONCAT()
    		    when 16
    		        # 1:76: PERCENT
    		        match_PERCENT()
    		    when 17
    		        # 1:84: POWER
    		        match_POWER()
    		    when 18
    		        # 1:90: BANG
    		        match_BANG()
    		    when 19
    		        # 1:95: DIGIT
    		        match_DIGIT()
    		    when 20
    		        # 1:101: INT_CONST
    		        match_INT_CONST()
    		    when 21
    		        # 1:111: NUM_CONST
    		        match_NUM_CONST()
    		    when 22
    		        # 1:121: STR_CONST
    		        match_STR_CONST()
    		    when 23
    		        # 1:131: REF2D
    		        match_REF2D()
    		    when 24
    		        # 1:137: TRUE_CONST
    		        match_TRUE_CONST()
    		    when 25
    		        # 1:148: FALSE_CONST
    		        match_FALSE_CONST()
    		    when 26
    		        # 1:160: NAME
    		        match_NAME()
    		    when 27
    		        # 1:165: QUOTENAME
    		        match_QUOTENAME()
    		    when 28
    		        # 1:175: FUNC_IF
    		        match_FUNC_IF()
    		    when 29
    		        # 1:183: FUNC_CHOOSE
    		        match_FUNC_CHOOSE()
    		end

    end


	    class DFA
	        def initialize(eot, eof, min, max, accept, special, transition)
	            @eot = eot
	            @eof = eof
	            @min = min
	            @max = max
	            @accept = accept
	            @special = special
	            @transition = transition
	        end

	        def predict(parser, input)
	            mark = input.mark()
	            s = 0 # we always start at s0
	            begin
	                loop do
	                    special_state = @special[s]
	                    if special_state >= 0
	                        s = parser.special_state_transition(special_state)
	                        input.consume()
	                        next
	                    end

	                    if @accept[s] >= 1
	                        return @accept[s]
	                    end

	                    # look for a normal char transition
	                    c = input.look_ahead(1).to_i
	                    if c != :EOF && c >= @min[s] && c <= @max[s]
	                        next_state = @transition[s][c - @min[s]] # move to next state
	                        if next_state < 0
	                            # was in range but not a normal transition
	                            # must check EOT, which is like the else clause.
	                            # eot[s]>=0 indicates that an EOT edge goes to another
	                            # state.
	                            if @eot[s] >= 0  # EOT Transition to accept state?
	                                s = @eot[s]
	                                input.consume()
	                                next
	                            end
	                            raise "No viable alt"
	                        end
	                        s = next_state
	                        input.consume()
	                        next
	                    end
	                    if @eot[s] >= 0   # EOT Transition?
	                        s = @eot[s]
	                        input.consume()
	                        next
	                    end
	                    if c == :EOF && @eof[s] >= 0   # EOF Transition to accept state?
	                        return @accept[@eof[s]]
	                    end

	                    # not in range and not EOF/EOT, must be invalid symbol
	                    raise "No viable alt"
	                end
	            ensure
	                input.rewind(mark)
	            end
	        end
	    end

    DFA11 = DFA.new(
        [-1,30,32,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,33,-1,-1,-1,-1,
         -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,38,-1,39,-1,-1,-1,-1],
        [-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
         -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1],
        [0,61,61,0,0,0,0,0,0,0,0,0,0,0,0,0,46,0,0,0,36,36,0,36,0,0,0,36,
         0,0,0,0,0,0,46,36,36,36,0,0,0],
        [116,62,61,0,0,0,0,0,0,0,0,0,0,0,0,0,57,0,0,0,97,114,0,90,0,0,0,
         90,0,0,0,0,0,0,57,108,57,79,0,0,0],
        [-1,-1,-1,6,7,8,9,10,11,12,13,14,15,16,17,18,-1,21,22,23,-1,-1,24,
         -1,25,26,27,-1,3,4,1,5,2,19,-1,-1,-1,-1,20,28,29],
        [-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
         -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1],
        [
            [25,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,15,18,-1,19,13,12,
                 26,10,11,5,3,9,4,17,6,16,16,16,16,16,16,16,16,16,16,7,8,
                 1,-1,2,-1,-1,19,19,27,19,19,20,19,19,23,19,19,19,19,19,
                 19,19,19,19,19,21,19,19,19,19,19,19,-1,-1,-1,14,-1,-1,-1,
                 -1,-1,-1,-1,24,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,22],
            [29,28],
            [31],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [],
            [17,-1,34,34,34,34,34,34,34,34,34,34],
            [],
            [],
            [],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19,-1,-1,-1,-1,-1,-1,-1,35,19,19,19,19,19,19,19,19,19,
                 19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,-1,-1,-1,
                 -1,-1,-1,24],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,-1,-1,-1,-1,-1,-1,22,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,22],
            [],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,36,19,19,19,19,
                 19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19],
            [],
            [],
            [],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,37,19,19,
                 19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19],
            [],
            [],
            [],
            [],
            [],
            [],
            [17,-1,34,34,34,34,34,34,34,34,34,34],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,24,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,24],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19],
            [19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,19,19,19,19,19,19,19,19,
                 19,19,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
                 -1,-1,-1,-1,40],
            [],
            [],
            []
        ])

    def special_state_transition(s)
    		-1
    end

    public :special_state_transition
end