0

我只是在学习 Ruby 并且很难解决这个错误,我读了一些帖子,都说要定义这样的方法......

def self.methodname

我这样做了,但无济于事。这是我的代码希望这是我缺少的一件简单的事情。谢谢您的帮助。

class Cannibals
@VEGANS = 3
@CANNIBALS = 3
@VEGAN_ID = 0
@CANNIBAL_ID = 1
@EMPTY_ID = 2
@CROSSED_ID = 0
@SHORE_ID = 1

@vegansCrossed=0
@cannibalsCrossed=0
@vegansLeft = @VEGANS
@cannibalsLeft = @CANNIBALS
@boat = [@EMPTY_ID,@EMPTY_ID]
@boatLocation = @SHORE_ID


#/* take an integer as argument1, 
# * 0- load 2 cannibals
# * 1- load 2 vegans
# * 2- load one of each.
# * 3- load 1 cannibal
# * 4- load 1 vegan 
# * argument 2 is destionation
# * 0- crossed
# * 1- shore*/
def self.populateBoat (choice,destination )
    message = "Invalid arguments delivered"
    boatDestination

    validChoice = false
case choice
    when 0
        validChoice = true
        if destination == @CROSSED_ID
            @cannibalsLeft -= 2
        elsif destination == @SHORE_ID 
            @cannibalsCrossed -=2
        end
        @boat[0] = @CANNIBAL_ID
        @boat[1] = @CANNIBAL_ID

    when 1
        validChoice = true
        if destination == @CROSSED_ID
            @vegansLeft -= 2
            elsif destination == @SHORE_ID 
            @vegansCrossed -= 2
        end
        @boat[0] = @VEGAN_ID
        @boat[1] = @VEGAN_ID
    when 2
        validChoice = true
        if destination == @CROSSED_ID
            --@vegansLeft
            --@cannibalsLeft
            elsif destination == @SHORE_ID
                --@vegansCrossed
                --@cannibalsCrossed
        end
        @boat[0] = @VEGAN_ID
        @boat[1] = @CANNIBAL_ID
    when 3
        validChoice = true
        if destination == @CROSSED_ID
            --@cannibalsLeft
            elsif destination == @SHORE_ID 

            --@cannibalsCrossed
        end

        @boat[0] = @CANNIBAL_ID
        @boat[1] = @EMPTY_ID
    when 4
        validChoice = true
        if destination == @CROSSED_ID 

            --@vegansLeft
            elsif destination == @SHORE_ID 

            --@vegansCrossed
        end

        @boat[0] = @VEGAN_ID
        @boat[1] = @EMPTY_ID
    else
        message = "Invalid choice"
end
    if validChoice 

        if destination == @SHORE_ID 
            boatDestination = "the starting point."
            elsif destination == @CROSSED_ID 
                boatDestination = "the ending point."
        else
            boatDestination = "a place unknown, they're off track."
        message = @getBoatOccupants   + "heading to " + boatDestination +"\n"
        end
    end
    return message

end
#/*Unload the boat, takes an integer for an argument
# * 0- unload crossed
# * 1- unload at shore */
def unloadBoat (where) 


    #create message
    String message = "They sunk the boat. \n"
    if @boatLocation == @SHORE_ID 
        message = "Boat unloaded at ending point. \n"

        elsif @boatLocation == @CROSSED_ID 
            message = "Boat unloaded at starting point. \n"
    end

    i = 0
    if where == @CROSSED_ID 
        for i in 0..1 
            if @boat[i] == @VEGAN_ID 
                @vegansCrossed += 1
            end
            if @boat[i] == @CANNIBAL_ID 
                @cannibalsCrossed += 1
            end
            @boat[i]=@EMPTY_ID
        end
        @boatLocation = @CROSSED_ID
        elsif where == @SHORE_ID        

            for i in 0..1 

                if @boat[i] == @VEGAN_ID 

                    @vegansLeft += 1
                    elsif @boat[i] == @CANNIBAL_ID 

                        @cannibalsLeft+= 1
                end
                @boat[i]=@EMPTY_ID
            end
            @boatLocation = @SHORE_ID
    end

    return message
end


#build a string describing boat's occupants.
def getBoatOccupants  

    message = ""
    occupants = Array.new(2)


    #Get names for occupants
    i = 0
    for i in 0..2

        occupants[i] = ""
        if @boat[i] == @VEGAN_ID 
            occupants[i] = "vegan"
        end
        if @boat[i] == @CANNIBAL_ID 
            occupants[i] = "cannibal"
        end

    end
    #if boat is full start building string
    if @boat[1] != @EMPTY_ID 


        if @boat[0] == @boat[1] 

            message = "Two " + occupants[0]
            message +=  "s are "
        else

            message =  "One "+occupants[0]
            message += " and one " + occupants[1] + " are "
        end

    #if boat is empty start building string
        elsif @boat[1] == @EMPTY_ID 

            message = "One "+occupants[0]
            message +=  " is "
    end
    message +=  "in the boat "
    return message
end
def getBoatPosition  

    String location = ""
    if @boatLocation == @SHORE_ID 
        location = "at the starting position."
        elsif @boatLocation == @CROSSED_ID 
            location = "across the river."
    end
    return location
end


#/*Check to see if game is over and i programmed it wrong perfectGameLogic  or if user got eaten. */
def eaten  

    boolean gameOver = false

    if  @cannibalsLeft > @vegansLeft and @vegansLeft != 0  ||  @cannibalsCrossed > @vegansCrossed and @vegansCrossed != 0  
        gameOver = true
    return gameOver
end

#/*Used for gamLogic playable  only
# * decides if a users choice is valid given the circumstances.
# */
def isValid  

    validChoices = [true, true, true, true, true]
    if @boatLocation == @SHORE_ID 

        case @cannibalsLeft 

            when 0
                validChoices[0] = false
                validChoices[2] = false
                validChoices[3] = false
            when 1
                validChoices[0] = false
            else #//do nothing.
        end
        case @vegansLeft 

            when 0
                validChoices[1] = false
                validChoices[2] = false
                validChoices[4] = false
            when 1
                validChoices[1] = false
            else #//do nothing.
        end
        elsif @boatLocation == @CROSSED_ID 

            case @cannibalsCrossed 

                when 0
                    validChoices[0] = false
                    validChoices[2] = false
                    validChoices[3] = false
                when 1
                    validChoices[0] = false
                default:# //do nothing.
            end
            case @vegansCrossed 

                when 0
                    validChoices[1] = false
                    validChoices[2] = false
                    validChoices[4] = false
                when 1
                    validChoices[1] = false
                else #//do nothing.
            end
    end

    return validChoices
end
#/*This is for a preset game where rules are strict.
#no user input is required.
#game must move all cannibals across first,
#then 2 humans across
#then bring back one of each
#then save last human.
#base case: everyone crossed */
def self.perfectGameLogic (run) 

    message = ""

    if run == false 

        message = "Game Over"   
    else

        if  (@cannibalsLeft == 3 || @cannibalsLeft == 2  and @vegansLeft == 3) 

            message = message + populateBoat(0, @CROSSED_ID) 
            message +=unloadBoat(@CROSSED_ID) 
            message +=populateBoat(3, @SHORE_ID) 
            message +=unloadBoat(@SHORE_ID) 
            elsif @vegansLeft == 3 and @cannibalsLeft == 1 

                message +=populateBoat(1, @CROSSED_ID) 
                message +=unloadBoat(@CROSSED_ID) 
                message +=populateBoat(2, @SHORE_ID) 
                message +=unloadBoat(@SHORE_ID) 
            elsif @vegansLeft == 2 and @cannibalsLeft == 2 

                message +=populateBoat(1, @CROSSED_ID) 
                message +=unloadBoat(@CROSSED_ID) 
            elsif @vegansCrossed == 3 and @cannibalsCrossed < 3 
                i = 0
                for i in 0..2

                    message +=populateBoat(3, @SHORE_ID) 
                    message +=unloadBoat(@SHORE_ID) 
                    message +=populateBoat(0, @CROSSED_ID) 
                    message +=unloadBoat(@CROSSED_ID) 
                end
            elsif @vegansCrossed == 3 and @cannibalsCrossed == 3 

                message = "You Win!"
                run = false
        end
        puts message 
        if @eaten   == true 

            puts "you lose" 
            run = false
        end

            perfectGameLogic(run) 


    end
end
#/* this is a game the user gets to interact with.
# * if you get eaten, game is over, or if you win, game is over.
# */
def self.gameLogic(run) 

     message = ""
     error = ""
     choice
     destination = @CROSSED_ID
     choiceOk = false
    isValid = @isValid  


    if run == false 

        message = "Game Over"   
    else

        if @vegansCrossed == 3 and @cannibalsCrossed == 3 

            puts  "You Win!" 
            run = false
        else

            begin
                putsln error+"\n" 
                message = "The boat is " + @getBoatPosition   + "\n" +
                            @vegansCrossed+ " vegans have crossed and \n"+
                            @cannibalsCrossed + " cannibals have crossed. \n"
                            +"Please make a choice, who goes on the boat?: \n" +
                            "0 - load 2 cannibals \n" + 
                            "1 - load 2 vegans \n" +
                            "2 - load one of each \n" +
                            "3 - load 1 cannibal \n" +
                            "4 - load 1 Vegan \n" 
                puts message   
                choice = scan.nextInt  

                if choice < 5 and choice >= 0 

                    if isValid[choice] 

                        #//this is the only case where a choice is acceptable.
                        choiceOk = true
                    else

                        error = "You can't move people who aren't there."
                    end
                else

                    error= "You must choose a number between 0 and 4."
                end
            end
            end while choiceOk == false 

            if @boatLocation == @SHORE_ID 
                destination = @CROSSED_ID
                elsif @boatLocation == @CROSSED_ID 
                    destination = @SHORE_ID
                end
            end

            populateBoat(choice, destination) 
            unloadBoat(destination) 
        end
        if @eaten == true 

            puts "You Lose, those poor vegans! :  " 
            run = false
        end

        gameLogic run 


    end
end


end

Game = Cannibals.new
    #/#perfectGameLogic just runs.
    #//gameLogic is playable.
    #Game.perfectGameLogic(true);
    puts "***********************************Cannibals and vegan river crossing******************************** \n" +
                            "the object of the game is to get all the vegans across the river safetly. If the cannibals out number \n " +
                            "the vegans, they will be eaten alive and you lose the game, so try to avoid that!"
    Game.populateBoat(0,0)                  
    #Game.gameLogic(true)

这是我第一次尝试 ruby​​,以前这是用 java 编码的,所以如果我错过了代码中的 java 特定内容,请原谅我。并给我一些指导,谢谢!

4

1 回答 1

1

在类内部,使用以下方法声明的方法:

class MyClass
  def self.my_method
    # some stuff...
  end
end

是一种“类方法”。这意味着你可以这样称呼它:

MyClass.my_method

拥有一个与类成员相关联的“实例方法”也是有效的,而不是类本身:

class MyClass
  def my_method
    # some stuff
  end
end

在你的情况下,我认为你在“这里的一些其他代码......”中的代码可能有语法错误和额外的end语句,过早关闭类并导致def self.gameLogic(...)无效,因为它不在班上。

在您使用 a 创建类方法(如上所述)的逻辑中存在明显错误,def self.gameLogic但您调用它时就好像它是具有类实例的实例方法一样。您应该将类​​方法称为Cannibals.gameLogic(...),或声明gameLogic为实例方法:def gameLogic(...)在类中。

于 2013-06-01T04:08:05.070 回答