#function #arraylist #function-pointers #fitness
#функция #arraylist #указатели на функции #Фитнес
Вопрос:
Я прочитал несколько сообщений об указателях на функции, но я все еще не понимаю, как использовать «указатели на функции» наилучшим образом для моего случая. Также в этом случае мне непонятно использование анонимных классов…
Здесь код:
class Fitness {
private List < Double > list;
interface Foo {
//public Foo;
Object myFunc(Object arg);
Object myFunc2(Object arg);
}
public Fitness(List < Double > list) {
this.list = new ArrayList < Double > (list);
}
public void bar(Foo foo) {
Object object = foo.myFunc(list);
System.out.println(object);
Object object2 = foo.myFunc2(list);
System.out.println(object2);
}
public void method(String func) {
if (func.equals("f1"))
bar(
new Foo() {
public Object myFunc(Object arg) {
return (Double)((List) arg).get(0) 50.0;
}
public Object myFunc2(Object arg) {
return (Double)((List) arg).get(0) 50.0;
}
});
else if (func.equals("f2"))
bar(
new Foo() {
public Object myFunc(Object arg) {
List < Double > l = (List < Double > ) arg;
return l.get(0) / l.size();
}
public Object myFunc2(Object arg) {
List < Double > l = (List < Double > ) arg;
return l.get(0) / l.size();
}
});
}
public void fitness1() {
bar(
new Foo() {
public Object myFunc(Object arg) {
return (Double)((List) arg).get(0) 50.0 * 1000;
}
public Object myFunc2(Object arg) {
return (Double)((List) arg).get(0) 50.0;
}
});
}
}
class Example {
public static void main(String[] args) {
ArrayList < Double > listD = new ArrayList < Double > ();
listD.add(100.0);
listD.add(-1.0);
listD.add(-5.0);
Fitness t = new Fitness(listD);
//t.method("f1");
//t.method("f2");
//t.method2();
t.fitness1();
}
}
То, что я хотел бы, — это соответствие объекта, которое вызывает функцию соответствия в соответствии с некоторыми параметрами. Метод пригодности должен иметь возможность принимать список int, double, даже couple <int, String> .
Я хочу выполнить тест: поэтому я хочу увидеть разные результаты, если я выберу f1, f2, f3, f4. Я не понимаю, как это закодировать.
Заранее спасибо
Ответ №1:
Вы можете объявить следующий интерфейс:
interface FooFunc {
Object invoke(Foo foo, Object arg);
}
Затем слегка измените свой метод bar():
public void bar(Foo foo, FooFunc func) {
Object object = func.invoke(foo, list);
System.out.println(object);
}
… и ваш метод fitness1():
public void fitness1(FooFunc func) {
bar(
new Foo() {
public Object myFunc(Object arg) {
return (Double) ((List) arg).get(0) 50.0 * 1000;
}
public Object myFunc2(Object arg) {
return (Double) ((List) arg).get(0) 50.0;
}
}, func);
}
Теперь, из вашего метода main(), вы можете сделать:
Fitness t = new Fitness(listD);
t.fitness1(Fitness.Foo::myFunc);
t.fitness1(Fitness.Foo::myFunc2);
Разве это не здорово?
ОБНОВЛЕНИЕ: полный файл
import java.util.ArrayList;
import java.util.List;
class Fitness {
private List<Double> list;
interface Foo {
//public Foo;
Object myFunc(Object arg);
Object myFunc2(Object arg);
}
interface FooFunc {
Object invoke(Foo foo, Object arg);
}
public Fitness(List<Double> list) {
this.list = new ArrayList<Double>(list);
}
public void bar(Foo foo, FooFunc func) {
Object object = func.invoke(foo, list);
System.out.println(object);
}
public void fitness1(FooFunc func) {
bar(
new Foo() {
public Object myFunc(Object arg) {
return (Double) ((List) arg).get(0) 50.0 * 1000;
}
public Object myFunc2(Object arg) {
return (Double) ((List) arg).get(0) 50.0;
}
}, func);
}
}
public class Example {
public static void main(String[] args) {
ArrayList<Double> listD = new ArrayList<>();
listD.add(100.0);
listD.add(-1.0);
listD.add(-5.0);
Fitness t = new Fitness(listD);
t.fitness1(Fitness.Foo::myFunc);
t.fitness1(Fitness.Foo::myFunc2);
}
}
Комментарии:
1. Здравствуйте, я не понимаю, является ли это более ясным решением, но оно выдает мне ошибку 2 (ту же): метод bar в class Test не может быть применен к заданным типам; bar( ^ требуется: Foo,FooFunc найдено: <анонимный Foo> причина: списки фактических и формальных аргументов отличаются по длине
2. @mickey это не дает мне никакой ошибки, но дает мне 50100,0 и 150,0
3. @mickey Я не вижу ни одного вызываемого класса
Test
. Я добавил полный файл, который я использовал в обновлении, в свой пост.4. Извините, я работал. Но в моем первом почтовом коде у меня было еще 2 функции «bar». Это дало мне ошибку! (функция ‘bar’s whithin’method’ …..) Любое улучшение, может быть, с помощью lambd?. Это намного сложнее, чем язык C….
5. @mickey Привет. Java — это не C. В Java нет такого понятия, как указатель на функцию; только объекты.