70

Homework: Rock Paper Scissors game.

I've created an enumeration:

      enum Gesture{ROCK,PAPER,SCISSORS};

from which I want to compare values to decide who wins--computer or human. Setting the values works just fine, and the comparisons work properly (paper covers rock, rock crushes scissors, scissors cuts paper). However, I cannot get my tie to work. The user is declared as the winner any time there's a tie.

Ahhh...crap...this will clarify: userPick is a String with values rock, paper, or scissors. I'm unable to use == to compare userPick to computerPick, which, as you can see below, is cast as type Gesture from my enum.

      if(computer == 1)
         computerPick = Gesture.ROCK;
      else
         if(computer == 2)
           computerPick = Gesture.PAPER;
         else
           computerPick = Gesture.SCISSORS;
      if(userPick.equals(computerPick))
       {
          msg = "tie";
          ++tieGames;
       }
           etc....

I am guessing that there's an issue with rock not being equal to ROCK, or the String userPick not being able to match Gesture computerPick because the latter isn't a String. However, I'm not able to find an example of a similar circumstance in my textbook or Oracle's Java Tutorials, so I'm not sure how to correct the problem...

Any hints?

3
  • 4
    You're right, you can't compare the string "rock" to the enum Gesture.ROCK. You'd need some sort of a string -> Gesture mapping function so that you can compare two enums. Luckily, Java already provides one. Try Gesture.valueOf([your_string]). If I recall correctly, this function is case sensitive. But I could be wrong.
    – K Mehta
    Commented Mar 25, 2012 at 5:33
  • 1
    That function is case sensitive. Thanks! Commented Mar 9, 2017 at 18:23
  • wouldn't it be enough to convert enum to string using .toString() method as Gesture.ROCK.toString().equals("ROCK") ? Commented May 18, 2022 at 6:31

11 Answers 11

70

I'm gathering from your question that userPick is a String value. You can compare it like this:

if (userPick.equalsIgnoreCase(computerPick.name())) . . .

As an aside, if you are guaranteed that computer is always one of the values 1, 2, or 3 (and nothing else), you can convert it to a Gesture enum with:

Gesture computerPick = Gesture.values()[computer - 1];
4
  • @Ted Hopp: Lovely, lovely answer. Thanks so much. One followup question, though...what does the .name at the end of computerPick ~do~? I'm assuming this is something that points to a specific instance of computerPick? I'm trying to understand what this does that differentiates it from if (userPick.equalsIgnoreCase(computerPick())). thanks!
    – dwwilson66
    Commented Mar 25, 2012 at 5:49
  • @dwwilson66 - If computerPick is an enum value of type Gesture, then computerPick().name() returns a String with the symbolic name of the current value of computerPick. (That is, if computerPick == Gesture.ROCK, then computerPick.name() will be the string "ROCK". (Every enum type has instance methods name() and ordinal() generated by the compiler. The type also has static methods values() and valueOf(String) automatically generated. See the Java Language Specification.
    – Ted Hopp
    Commented Mar 25, 2012 at 6:47
  • Nice. Thanks. That makes a lot of sense. name(), of course, is not included in my textbook, which seems to sacrifice detail for readability more often than not.... :\
    – dwwilson66
    Commented Mar 25, 2012 at 15:10
  • I am using java 8 and when I chose .name(), I see this - Returns the name of this enum constant, exactly as declared in its enum declaration. Most programmers should use the toString method in preference to this one, as the toString method may return a more user-friendly name. This method is designed primarily for use in specialized situations where correctness depends on getting the exact name, which will not vary from release to release. Returns: the name of this enum constant
    – jmathewt
    Commented Nov 27, 2018 at 11:20
26

You should declare toString() and valueOf() method in enum.

 import java.io.Serializable;

public enum Gesture implements Serializable {
    ROCK,PAPER,SCISSORS;

    public String toString(){
        switch(this){
        case ROCK :
            return "Rock";
        case PAPER :
            return "Paper";
        case SCISSORS :
            return "Scissors";
        }
        return null;
    }

    public static Gesture valueOf(Class<Gesture> enumType, String value){
        if(value.equalsIgnoreCase(ROCK.toString()))
            return Gesture.ROCK;
        else if(value.equalsIgnoreCase(PAPER.toString()))
            return Gesture.PAPER;
        else if(value.equalsIgnoreCase(SCISSORS.toString()))
            return Gesture.SCISSORS;
        else
            return null;
    }
}
3
  • 2
    This is a great example, in Java 7 the valueOf method has been implemented in Enum. It works the same as your example though.
    – Evan
    Commented Jun 8, 2013 at 14:27
  • 9
    According to the Java Language Specification §8.9.2, each enum type declaration automatically generates a static valueOf(String) that behaves like your method (except it throws an exception instead of returning null and is case sensitive). Each enum constant also inherits from Enum the method name() which behaves similarly to your toString() (returning the exact name of the enum constant). @Evan - valueOf has been part of the Enum class since enums were introduced into Java; it's not new to Java 7.
    – Ted Hopp
    Commented Jul 26, 2013 at 15:47
  • This is useful for cases where the enums contain an underscore and you need a comparison....definitely helped me thank you....
    – Grim
    Commented May 31, 2017 at 19:19
12

My idea:

public enum SomeKindOfEnum{
    ENUM_NAME("initialValue");

    private String value;

    SomeKindOfEnum(String value){
        this.value = value;
    }

    public boolean equalValue(String passedValue){
        return this.value.equals(passedValue);
    }
}

And if u want to check Value u write:

SomeKindOfEnum.ENUM_NAME.equalValue("initialValue")

Kinda looks nice for me :). Maybe somebody will find it useful.

0
7
public class Main {

    enum Vehical{
        Car,
        Bus,
        Van
    }

    public static void main(String[] args){

      String vehicalType = "CAR";

        if(vehicalType.equals(Vehical.Car.name())){
            System.out.println("The provider is Car");
        }

     String vehical_Type = "BUS";

       if(vehical_Type.equals(Vehical.Bus.toString())){
            System.out.println("The provider is Bus");
        }


    }
}
5

Define enum:

public enum Gesture
{
    ROCK, PAPER, SCISSORS;
}

Define a method to check enum content:

private boolean enumContainsValue(String value)
{
    for (Gesture gesture : Gesture.values())
    {
        if (gesture.name().equals(value))
        {
            return true;
        }
    }

    return false;
}

And use it:

String gestureString = "PAPER";

if (enumContainsValue(gestureString))
{
    Gesture gestureId = Gesture.valueOf(gestureString);

    switch (gestureId)
    {
        case ROCK:
            Log.i("TAG", "ROCK");
            break;

        case PAPER:
            Log.i("TAG", "PAPER");
            break;

        case SCISSORS:
            Log.i("TAG", "SCISSORS");
            break;
    }
}
3

You can do it in a simpler way , like the below:

boolean IsEqualStringandEnum (String str,Enum enum)
{
  if (str.equals(enum.toString()))
     return true;
  else
     return false;
}
2
  • 7
    why not return str.equals(enum.toString()) and then why not simply use that expression?
    – Dude
    Commented Sep 6, 2016 at 6:13
  • For a method that starts with 'is' it is preferred that it returns boolean all the time. Commented Jun 26, 2017 at 15:50
2

This is my solution in java 8:

 public static Boolean isValidCity(String cityCode) {
        return Arrays.stream(CITY_ENUM.values())
                .map(CITY_ENUM::getCityCode)
                .anyMatch(cityCode::equals);
 }
0

This seems to be clean.

public enum Plane{

/**
 * BOEING_747 plane.
 */
BOEING_747("BOEING_747"),

/**
 * AIRBUS_A380 Plane.
 */
AIRBUS_A380("AIRBUS_A380"),

;

private final String plane;       

private Plane(final String plane) {
    this.plane= plane;
}

Plane(){ 
    plane=null; 
}


/**
 * toString method.
 * 
 * @return Value of this Enum as String.
 */
@Override
public String toString(){
   return plane;
}

/**
 * This method add support to compare Strings with the equalsIgnoreCase String method.
 * 
 * Replicated functionality of the equalsIgnorecase of the java.lang.String.class
 * 
 * @param value String to test.
 * @return True if equal otherwise false.
 */
public boolean equalsIgnoreCase(final String value){
    return plane.equalsIgnoreCase(value);
}

And then in main code:

String airplane="BOEING_747";

if(Plane.BOEING_747.equalsIgnoreCase(airplane)){
     //code
}
1
  • Seems to me you went to great lengths to overload the Enum to just change the behavior slightly. Commented Jun 26, 2017 at 15:53
0

Doing an static import of the GestureTypes and then using the valuesOf() method could make it look much cleaner:

enum GestureTypes{ROCK,PAPER,SCISSORS};

and

import static com.example.GestureTypes.*;
public class GestureFactory {

    public static Gesture getInstance(final String gesture) {
        if (ROCK == valueOf(gesture))
            //do somthing
        if (PAPER == valueOf(gesture))
            //do somthing
    }
}
-1

You can compare a string to an enum item as follow,

public class Main {

    enum IaaSProvider{
        aws,
        microsoft,
        google
    }

    public static void main(String[] args){

        IaaSProvider iaaSProvider = IaaSProvider.google;

        if("google".equals(iaaSProvider.toString())){
            System.out.println("The provider is google");
        }

    }
}
2
  • Trying to use a string like that in an equals comparison will likely not work. Even if it does you should really set it to a variable.
    – KHeaney
    Commented Mar 4, 2015 at 14:46
  • 1
    Nothing wrong with using string values like that, maybe is not pretty. And "google".equals(...) compiles no problem. Commented Jun 26, 2017 at 15:55
-4

You can use equals().

enum.equals(String)

1
  • Intellij idea does not recommend this approach. It prompts out the following message ` 'equals()' between objects of inconvertible types 'FareType' and 'String' ` Commented Feb 18, 2020 at 12:53

Not the answer you're looking for? Browse other questions tagged or ask your own question.