[英]Why can't java find my method?
我正试图围绕 java 中的一些东西。 当我将 object 传递给另一个类的方法时,我不能只调用 object class 固有的任何方法吗?
如下示例代码无法编译的原因是什么?
谢谢,
class a {
public static void myMethod(Object myObj) {
myObj.testing();
}
}
class b {
public void testing() {
System.out.println ("TESTING!!!");
}
}
class c {
public static void main (String[] args) {
b myB = new b();
a.myMethod(myB);
}
}
编辑:我将 myMethod 中的参数保留为 Object 类型的原因是因为我希望能够传入各种 object 类型,每个类型都有一个 testing() 方法。
如果你想通过testing()
方法传入各种对象,让每个 object 实现一个Testable
接口:
public interface Testable
{
public void testing()
}
然后让myMethod()
拿一个Testable
。
public static void myMethod(Testable testable)
{
testable.testing();
}
编辑:为了澄清,实现一个接口意味着 class 保证拥有该方法,但该方法可以为所欲为。 所以我可以有两个类,它们的testing()
方法做不同的事情。
public class AClass implements Testable
{
public void testing()
{
System.out.println("Hello world");
}
}
public class BClass implements Testable
{
public void testing()
{
System.out.println("Hello underworld");
}
}
问题是myMethod
在实际运行之前无法知道它得到了 a b
object。 你可以传入一个String
,因为它知道。
将其更改为
public static void myMethod(b myObj) {
myObj.testing();
}
它应该可以工作。
问题更新:
编辑:我将 myMethod 中的参数保留为 Object 类型的原因是因为我希望能够传入各种 object 类型,每个类型都有一个 testing() 方法。
正如 Amanda S 和其他几个人所说,这是一个完美的界面案例。 这样做的方法是创建一个定义testing()
方法的接口并更改myMethod
以获取实现该接口的对象。
另一种解决方案(无接口)是反思性地发现 object 是否具有testing()
方法并调用它,但对于这样一个简单的情况,不建议这样做,也不需要这样做。
你在说的是鸭子打字。 Java 没有鸭子类型。
因此,您需要定义一个所有具有testing()
方法的类都实现的接口。
例如:
public interface Testable
{
public void testing()
}
class B implements Testable
{
public void testing() {
System.out.println ("TESTING!!!");
}
}
class A {
public static void myMethod(Testable myObj) {
myObj.testing();
}
}
您的问题是支持接口的经典论点。 您希望尽可能通用,但您希望通过的每个 object 都有一个 testing() 方法。 我建议以下内容:
public interface Testable
{
public void testing();
}
public class A
{
public static void myMethod(Testable myObj)
{
myObj.testing();
}
}
public class B implements Testable
{
public void testing()
{
System.out.println("This is class B");
}
}
public class C implements Testable
{
public void testing()
{
System.out.println("This is class C");
}
}
public class Test
{
public static void main (String[] args)
{
B myB = new B();
C myC = new C();
A.myMethod(myB); // "This is class B"
A.myMethod(myC); // "This is class C"
}
}
因为您传入的是 Object(b 继承自 Object)。 Object 没有测试,b 有。
在调用该方法之前,您可以传入 b 或将 object 转换为 b。
编辑要传入实现该方法的通用 class:您需要创建一个具有方法签名的接口并传入接口类型而不是 Object。 您传入的所有对象都必须实现该接口。
您只能访问对 object 的引用类型可见的成员。
在myMethod(Object myObj)
的情况下,这意味着只有 Object 中定义的成员,因此在class a
中class b
的成员将不可见。
如果您将a.myMethod
的定义更改为public static void myMethod(b myObj)
您将能够在myMethod
中看到b
实例上的testing
方法。
根据澄清更新:
在这种情况下,为所有这些定义一个接口来实现可能是您想要的。
public interface Testable {
public void testing();
}
public class a {
public static void myMethod(Testable myObj) {
myObj.testing();
}
}
public class b implements Testable {
public void testing () {
System.out.println("TESTING!!!");
}
}
为什么java找不到我的方法?
由于 Java 的设计方式。
Java 是“静态类型的” ,这意味着在编译期间检查对象类型。
在 Java 中,只有当该方法属于该类型时,您才能调用该方法。
由于此验证是在编译期间进行的,并且 Object 类型没有“testing()”方法,因此编译失败(即使在运行时对象确实具有该方法)。这主要是为了安全。
其他人描述的解决方法将要求您创建一个新类型,您可以在其中告诉编译器
“嘿,这种类型的实例会响应测试方法”
如果您想传递各种对象并保持其非常通用,一种方法是让这些对象实现和接口。
public interface Testable {
public void testing();
}
class A implements Testable { // here this class commits to respond to "testing" message
public void testing() {
}
}
class B implements Testable { // B "is" testable
public void testing() {
System.out.println("Testing from b");
}
}
class C implements Testable { // C is... etc.
public void testing() {
//....
}
}
后来在别的地方
public void doTest( Testable object ) {
object.testing();
}
doTest( new A() );
doTest( new B() );
doTest( new C() );
在 java 中执行此操作的“其他”方式正在反射地调用方法,但我不确定这是否是您需要的,因为当您这样做时代码更加抽象,但这就是自动化测试框架的方式(和许多其他框架(例如 Hibernate)确实有效。
我希望这可以帮助您澄清原因。
如果你真的,真的想尽可能地保持参数抽象,你应该考虑反射 API。 这样,您可以传递您想要的任何 object 并动态执行您想要的方法。 你可以看看一些例子。
这不是唯一的方法,但根据您的问题,它可能是一种有效的替代方法。
请记住,反射比直接调用您的方法要慢得多。 您也可以考虑使用界面,例如 Amanda 帖子中的界面。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.