Java Pass方法作为参数

我正在寻找一种通过引用来传递方法的方法。 我明白,Java不会将方法作为参数传递,但是,我想获得替代方法。

我被告知接口是传递方法作为参数的替代方法,但我不明白接口如何作为引用的方法。 如果我理解正确,接口只是一组未定义的抽象方法。 我不想发送每次都需要定义的接口,因为几种不同的方法可以用相同的参数调用相同的方法。

我想要做的是类似于这样的事情:

public void setAllComponents(Component[] myComponentArray, Method myMethod) {
    for (Component leaf : myComponentArray) {
        if (leaf instanceof Container) { //recursive call if Container
            Container node = (Container) leaf;
            setAllComponents(node.getComponents(), myMethod);
        } //end if node
        myMethod(leaf);
    } //end looping through components
}

调用如:

setAllComponents(this.getComponents(), changeColor());
setAllComponents(this.getComponents(), changeSize());

编辑:从Java 8开始,lambda表达式是其他答案指出的一个很好的解决方案。 下面的答案是为Java 7和更早的版本编写的...


看看命令模式。

// NOTE: code not tested, but I believe this is valid java...
public class CommandExample 
{
    public interface Command 
    {
        public void execute(Object data);
    }

    public class PrintCommand implements Command 
    {
        public void execute(Object data) 
        {
            System.out.println(data.toString());
        }    
    }

    public static void callCommand(Command command, Object data) 
    {
        command.execute(data);
    }

    public static void main(String... args) 
    {
        callCommand(new PrintCommand(), "hello world");
    }
}

编辑:正如Pete Kirkham指出的,还有另一种使用Visitor进行此操作的方法。 访问者方法有一点涉及 - 你的节点都需要用acceptVisitor()方法来访问感知 - 但是如果你需要遍历一个更复杂的对象图,那么这是值得研究的。


在Java 8中,您现在可以使用Lambda表达式更轻松地传递一个方法。 首先,一些背景。 功能接口是一种只有一种抽象方法的接口,但它可以包含任意数量的默认方法(Java 8中的新增功能)和静态方法。 如果不使用lambda表达式,lambda表达式可以快速实现抽象方法,而不需要所有不必要的语法。

没有lambda表达式:

obj.aMethod(new AFunctionalInterface() {
    @Override
    public boolean anotherMethod(int i)
    {
        return i == 982
    }
});

使用lambda表达式:

obj.aMethod(i -> i == 982);

以下是关于Lambda表达式的Java教程的摘录:

Lambda表达式的语法

一个lambda表达式由以下内容组成:

  • 用逗号分隔的括号内的形式参数列表。 CheckPerson.test方法包含一个参数p,它代表Person类的一个实例。

    注意 :您可以省略lambda表达式中参数的数据类型。 另外,如果只有一个参数,则可以省略括号。 例如,下面的lambda表达式也是有效的:

    p -> p.getGender() == Person.Sex.MALE 
        && p.getAge() >= 18
        && p.getAge() <= 25
    
  • 箭头标记->

  • 一个由单个表达式或语句块组成的主体。 这个例子使用下面的表达式:

    p.getGender() == Person.Sex.MALE 
        && p.getAge() >= 18
        && p.getAge() <= 25
    

    如果您指定单个表达式,则Java运行时将评估表达式并返回其值。 或者,您可以使用return语句:

    p -> {
        return p.getGender() == Person.Sex.MALE
            && p.getAge() >= 18
            && p.getAge() <= 25;
    }
    

    返回语句不是表达式; 在lambda表达式中,您必须将语句括在大括号({})中。 但是,您不必在花括号中包含void方法调用。 例如,以下是有效的lambda表达式:

    email -> System.out.println(email)
    
  • 请注意,lambda表达式看起来很像方法声明; 您可以将lambda表达式视为匿名方法 - 没有名称的方法。


    以下是如何使用lambda表达式“传递方法”:

    interface I {
        public void myMethod(Component component);
    }
    
    class A {
        public void changeColor(Component component) {
            // code here
        }
    
        public void changeSize(Component component) {
            // code here
        }
    }
    
    class B {
        public void setAllComponents(Component[] myComponentArray, I myMethodsInterface) {
            for(Component leaf : myComponentArray) {
                if(leaf instanceof Container) { // recursive call if Container
                    Container node = (Container)leaf;
                    setAllComponents(node.getComponents(), myMethodInterface);
                } // end if node
                myMethodsInterface.myMethod(leaf);
            } // end looping through components
        }
    }
    
    class C {
        A a = new A();
        B b = new B();
    
        public C() {
            b.setAllComponents(this.getComponents(), component -> a.changeColor(component));
            b.setAllComponents(this.getComponents(), component -> a.changeSize(component));
        }
    }
    

    使用java.lang.reflect.Method对象并调用invoke

    链接地址: http://www.djcxy.com/p/47309.html

    上一篇: Java Pass Method as Parameter

    下一篇: Use awk to convert GPS Position to Latitude & Longitude