Approaches to persist enum in java

34 views Asked by At

Good afternoon everyone,

I'm doing an api to order participants in different competitions. The competitions have different trials, for example, push-ups and run. The point is that trials can be measured in different ways, in this case, push-ups in reps and run in seconds, so I guess the best way of doing this is having a method that can be override, lets say getRating(int mark), where mark would be 5 push ups or 10 seconds. That method will return the rating the athlete will have in that trial.

From my point of view, I have two approaches. The first one is using an enum, but since I want to persist the info, I'm not quite sure about how to do it. I've seen that i need to use the @Enumerated notation here. This I think will solve the problem but if I want to get information about the trials after (name, description or any other attribute I include), will I have problems since they are not in the DB? Also it is important to notice that if there is only one competition this won't be really a problem, but if the number starts to grow, the number of trials will increase even more, so I don't really know if this is the best approach.

This would be something similar to this:

public enum Trial {
    PUSH_UPS("Push-ups", "Test your upper body strength by doing push-ups.") {
        @Override
        public String getRating(int result) {
            if (result >= 40) {
                return "Excellent";
            } else if (result >= 30) {
                return "Good";
            } else if (result >= 20) {
                return "Fair";
            } else {
                return "Poor";
            }
        }
    },
    PULL_UPS("Pull-ups", "Test your upper body strength by doing pull-ups.") {
        @Override
        public String getRating(int result) {
            if (result >= 20) {
                return "Excellent";
            } else if (result >= 15) {
                return "Good";
            } else if (result >= 10) {
                return "Fair";
            } else {
                return "Poor";
            }
        }
    },
    RUNNING("Running", "Test your cardiovascular endurance by running.") {
        @Override
        public String getRating(int result) {
            if (result <= 420) { // 7 minutes (420 seconds) for 1 mile
                return "Excellent";
            } else if (result <= 540) { // 9 minutes (540 seconds) for 1 mile
                return "Good";
            } else if (result <= 660) { // 11 minutes (660 seconds) for 1 mile
                return "Fair";
            } else {
                return "Poor";
            }
        }
    };

    private final String name;
    private final String description;

    Trial(String name, String description) {
        this.name = name;
        this.description = description;
    }

    public String getName() {
        return name;
    }

    public String getDescription() {
        return description;
    }

    public abstract String getRating(int result);
}

The second one is having an abstract class and extends from it every single trial. In order to persist I think a single table would be the best choice. From here I have a question, with this approach do I need a single Service, a single DAO and a single Controller for every trial? Is there a way to simplify this structure?

This would be the abstract class

public abstract class Trial {
    private final String name;
    private final String description;

    protected Trial(String name, String description) {
        this.name = name;
        this.description = description;
    }

    public String getName() {
        return name;
    }

    public String getDescription() {
        return description;
    }

    public abstract String getRating(int result);
}

This would be the trials:

public class PushUpsTrial extends Trial {
    public PushUpsTrial() {
        super("Push-ups", "Test your upper body strength by doing push-ups.");
    }

    @Override
    public String getRating(int result) {
        if (result >= 40) {
            return "Excellent";
        } else if (result >= 30) {
            return "Good";
        } else if (result >= 20) {
            return "Fair";
        } else {
            return "Poor";
        }
    }
}

public class PullUpsTrial extends Trial {
    public PullUpsTrial() {
        super("Pull-ups", "Test your upper body strength by doing pull-ups.");
    }

    @Override
    public String getRating(int result) {
        if (result >= 20) {
            return "Excellent";
        } else if (result >= 15) {
            return "Good";
        } else if (result >= 10) {
            return "Fair";
        } else {
            return "Poor";
        }
    }
}

public class RunningTrial extends Trial {
    public RunningTrial() {
        super("Running", "Test your cardiovascular endurance by running.");
    }

    @Override
    public String getRating(int result) {
        if (result <= 420) { // 7 minutes (420 seconds) for 1 mile
            return "Excellent";
        } else if (result <= 540) { // 9 minutes (540 seconds) for 1 mile
            return "Good";
        } else if (result <= 660) { // 11 minutes (660 seconds) for 1 mile
            return "Fair";
        } else {
            return "Poor";
        }
    }
}

So the question I'm asking is, which approach is better? Is there another better way of solving this problem? Is the solution the same in the end?

Thank you.

0

There are 0 answers