Java перегрузка: как позвонить конкретнее c один - PullRequest
1 голос
/ 07 апреля 2020

Моя программа анализирует WebAssembly инструкций и принимает решения на основе контекста текущей инструкции. Итак, MWE для моего алгоритма выглядит следующим образом:

public class Main {
    public interface Context {
        String name();
    }
    static class M implements Context {
        public String name() {
            return "Context M: ";
        }
    }
    static class N implements Context {
        public String name() {
            return "Context N: ";
        }
    }

    public interface Instruction {
        int getId();

        String run();
    }

    static class A implements Instruction {
        public int getId() {
            return 0;
        }

        public String run() {
            return "The work of A";
        }
    }

    static class B implements Instruction {
        public int getId() {
            return 1;
        }

        public String run() {
            return "The work of B";
        }
    }

    static void work(Context context, Instruction instruction) {
        switch (instruction.getId()) {
            case 0:
                workOnId0(context, (A) instruction);
                break;
            case 1:
                workOnId1(context, (B) instruction);
                break;
            default:
                throw new RuntimeException("Failed to recognize instruction");
        }
    }

    static void workOnId0(Context context, A instruction) {
        System.out.println(context.name() + instruction.run());
    }

    static void workOnId1(Context context, B instruction) {
        System.out.println(context.name() + instruction.run());
    }

    static void workOnId1(N context, B instruction) {
        System.out.println("This is corner case logic for this context!");
    }

    public static void main(String[] args) {
        N context = new N();
        B instruction = new B();

        work(context, instruction);
    }
}

Как вы можете видеть сверху, когда моя инструкция B, тогда обычная работа должна произойти в workOnId1, но в случае, если мой в частности, контекст N, я хотел бы выполнить некоторую специальную работу, которая представлена ​​другой перегрузкой workOnId1.

К сожалению, специальная перегрузка никогда не вызывается. Как я могу заставить работать разрешение перегрузки?

Ответы [ 2 ]

0 голосов
/ 07 апреля 2020

you can change one line under case:1 as below to achieve your target

switch (instruction.getId()) {
            case 0:
                workOnId0(context, (A) instruction);
                break;
            case 1:
                workOnId1((context instanceof N)? (N)context :context, (B) instruction);                break;
            default:
                throw new RuntimeException("Failed to recognize instruction");
        }
0 голосов
/ 07 апреля 2020

workOnId1(Context context, B instruction) будет вызываться всегда, потому что у вас есть объект Context.

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

if(context instanceof N) {
   workOnId1((N)context, (B)instruction);
} else {
   workOnId1(context, (B) instruction);
}
...