Проблема с использованием интерфейса в Java

делаю тестовое задание. и возник вопрос что я использую интерфейс Action в коде но метод hello в IDEA пишет что ни разу не использовался, в итоге как я не пытался(используя свой уровень знаний в Java) так и не смог добиться того чтобы метод использовался

package com.company;
import java.util.ArrayList;
import java.util.List;

abstract class Human {
     String name;
}

interface Action { // Создаём интерфейс с абстрактным методом для класса Candidate
    void hello();
}

class candidateExp1 {
    public static String selflearner() {
        return "I have been learning Java by myself, nobody examined how thorough is my knowledge and how good is my code";
    }
}

class candidateExp2 {
    public static String getJJ() {
        return "I passed successfully getJavaJob exams and code reviews";
    }
}

class Candidate implements Action {
    public String exp;
    public String name;

    public Candidate(String name, String exp) {
        this.name = name;
        this.exp = exp;
    }

    public  void setName(String name){
        this.name = name;
    }

    public String getName(){
        return name;          // Используем инкапсуляцию
    }

    public void setExp(String exp){
        this.exp = exp;
    }

    public void describeExperience() {
        if (exp.equals("self-learner")) {
            System.out.println(candidateExp1.selflearner());

        } else {
            System.out.println(candidateExp2.getJJ());
        }
    }

    @Override
    public void hello() {          // Используем метод интерфейса
        System.out.println("Hi, my name is " + this.name + "\n" + this.exp);
    }
}

class Employer extends Human {
    public void hello() {        // Используем абстракцию
        System.out.println("Hi! Introduce yourself");
    }
}

public class Main {
    public static void main(String[] args) {
        Employer employer = new Employer();
        List<Candidate> candidates = new ArrayList<>();

        candidates.add(new Candidate("Vasya","self-learner"));
        candidates.add(new Candidate("Petya","getJavaCourses"));
        candidates.add(new Candidate("Gabriel","self-learner"));

        for(Candidate candidate :candidates) {
                employer.hello();     // Используем абстракцию
                candidate.hello();    // Используем полиморфизм
                candidate.describeExperience();
            }
        }
    }
}

Ответы (1 шт):

Автор решения: Дмитрий

В вашем примере нет ООП. Вы просто наугад добавили интерфейс и абстрактный класс. Идея вам подсказывает верно : чтобы использовать метод интерфейса, нужно иметь переменную типа интерфейса, а у вас ее нет.

Для примера возьмем строчку кода:

Candidate сandidate = new Candidate("Vasya","self-learner")

В этом случае не имеет никакого значения, какие интерфейсы имплементирует класс Candidate, ведь мы созданный экземпляр класса поместили в переменную типа того же класса. У этого класса есть метод hello(), который мы вызовем в дальнейшем. Где здесь вызов метода интерфейса?

А теперь другой пример:

Action action = new Candidate("Vasya","self-learner")

Здесь все изменилось. Мы по прежнему создаем экземпляр класса Candidate, но помещаем его не в переменную типа Candidate, а в переменную типа Action , а это уже интерфейс, который данный класс имплементирует. Теперь мы у этой переменной вызовем метод hello(), таким образом, используем метод интерфейса, хотя фактически отработает переопределеный метод класса Candidate (вот это и есть полиморфизм).

Вы не присваиваете созданные экземпляры классов переменной Candidate , но ваша коллекция типизирована именно этим классом : List candidates, а не его интерфейсом : List candidates, поэтому вызов метода интерфейса и не происходит.

Я переделал ваш код, теперь он похож на что-то адекватное (и обратите внимание на замечания в комментариях, это очень важно, несмотря не то , что вам сейчас может показаться, что это мелочи).

import static com.company.Experience.*;
import java.util.ArrayList;
import java.util.List;

public class Main {

    public static void main(String[] args) {
        
        List<Action> actions = new ArrayList<>();
        actions.add(new Employer());
        actions.add(new Candidate("Vasya", SELF_LEARNER));
        actions.add(new Candidate("Petya", COURSES));
        actions.add(new Candidate("Gabriel", SELF_LEARNER));
        
        for (Action action : actions) System.out.println(action.hello());
        
    }
    
}

public class Candidate implements Action {

    private final String name;
    private final Experience experience;
    
    @Override
    public String hello() {
        return "Hi, my name is " + this.name + "\n" + experience.getDescription();
    }

    public Candidate(String name, Experience experience) {
        this.name = name;
        this.experience = experience;
    }
    
}

public class Employer implements Action {
    @Override
    public String hello() {
        return "Hi! Introduce yourself";
    }
}

public enum Experience {
    
    SELF_LEARNER ("I have been learning Java by myself, nobody examined how thorough is my knowledge and how good is my code"),
    COURSES ("I passed successfully getJavaJob exams and code reviews");
    
    private final String description;

    private Experience(String description) {
        this.description = description;
    }

    public String getDescription() {
        return description;
    }
    
}

public interface Action {
    String hello();    
}
→ Ссылка