有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

javascript如何在java中操作类

我懂sereval编程语言。其中大多数是脚本语言,如lua、perl、JS、ruby等

但最近,我开始用Java编程,它安静地工作。所以我一直在考虑JS中存在的某个函数。构造函数的原型,即。为了进一步了解我的问题到底是什么,我将用JS做一个例子。假设您想创建一个狗的应用程序

function dog (){
this.property1 = value;
this.propertr2 = value2;
this.propertyN = valueN;
//et.c.
}

//now, I will create sereval instances of the constructor in JS

var snoopy = new dog();
var buddy = new dog();

我所知道的关于JS的一点是,你可以动态地改变 构造函数和该构造函数的所有实例的信息 (在JS中称为prototype)的关键字如下:

dog.prototype.bark = function () {
console.log("Woof!");
};

这不仅改变了关于构造器的信息,使每个用构造器创造的狗都知道如何吠叫,而且也改变了构造器的所有实例都得到了原型插入的信息,在这种情况下,它教狗如何吠叫。我们可以在下一个示例中看到:

var someOtherDog = new dog ();
someOtherDog.bark(); //output will be: Woof!
snoopy.bark();       //output will also be: Woof!
buddy.bark();        //you guest it! it will also be: Woof!

So with this prototype keyword in JS I can manipulate constructors and their instances. Now, my question is:

如何在java中操作类及其实例?这可能吗? 若有,;为了在java中实现类似的功能,我应该做什么

class dog
{
    private String hairColor;
    public dog ()
    {
        hairColor = "Brown";
    }
    public static void main (String args[])
    {
        dog snoopy = new dog ();
        dog buddy = new dog ();
        //now, how do I manipulate the class like I did in JS?
    }
}

共 (3) 个答案

  1. # 1 楼答案

    问题是lua和JavaScript都是基于原型的,Java不是。您可以使用反射来完成类似的事情,但不能在JavaScript级别Reflection

  2. # 2 楼答案

    JavaScript中的继承由原型链完成。基本上,当在snoopy对象中找不到bark时,将在其原型snoopy.prototype中查找它。如果在那里找到,则使用该版本。如果不是(例如,在调用bark.toString()时),将遍历原型链,直到找到包含该成员的原型。原型本身在所有“实例”之间共享,因为它只是一个普通对象,所以以后可以向其添加或删除成员

    Java中的继承是基于类的。除非重新编译并重新加载整个类,否则无法在运行时从类定义中添加或删除成员。这是一种不同的编程范式,这意味着您必须使用其他技术和模式对其进行(稍微)不同的编程

  3. # 3 楼答案

    如果需要,可以动态创建匿名类

    假设你有一门课:

    class Dog {
        String name;
        Dog(String name) { this.name = name; }
        void bark() { System.out.println(name + " says 'woof!'"); }
    
        public static void main(String...args) { 
            Dog snoopy = new Dog("snoopy");
            snoopy.bark();
        }
    
    }
    

    这是结果

    c:\files\j>javac Dog.java
    
    c:\files\j>java Dog
    snoopy says 'woof!'
    

    现在,伙计,他不是说汪汪,而是说拉夫!所以我们像这样在飞行中创造了一个

    class Dog {
        String name;
        Dog(String name) { this.name = name; }
        void bark() { System.out.println(name + " says 'woof!'"); }
    
        public static void main(String...args) { 
            Dog snoopy = new Dog("snoopy");
            snoopy.bark();
            Dog buddy = new Dog("buddy") {
                @Override void bark() { System.out.println(name + " says 'ruff!'"); }
            };
            buddy.bark();
        }
    
    }
    

    导致

    c:\files\j>javac Dog.java
    
    c:\files\j>java Dog
    snoopy says 'woof!'
    buddy says 'ruff!'
    

    如果你想永久性地改变每只狗,这会变得更加困难,但可以通过策略模式来实现

    假设我们有以下几点

    abstract class BarkingStrategy {
        public abstract void doBark(Dog dog);
    }
    
    class TypicalBarkingStrategy extends BarkingStrategy {
        public void doBark(Dog dog) { System.out.println(dog.getName() + " says 'woof!'"); }
    }
    
    class AggressiveBarkingStrategy extends BarkingStrategy {
        public void doBark(Dog dog) { System.out.println(dog.getName() + " says 'Rrrruff!'"); }
    }
    
    class Dog {
        // notice this is static - that means it belongs to the class itself, not 
        // any particular instance of it - similar to prototype
        static BarkingStrategy bark = new TypicalBarkingStrategy();
        String name;
        Dog(String name) { this.name = name; }
        String getName() { return name; }
        void bark() { bark.doBark(this); }
    }
    

    然后您可以执行以下操作

    public static void main(String...args) {
        Dog snoopy = new Dog("snoopy");
        snoopy.bark();
        Dog.bark = new AggressiveBarkingStrategy();
        snoopy.bark();
    }
    

    这导致

    c:\files\j>javac Dog.java
    
    c:\files\j>java Dog
    snoopy says 'woof!'
    snoopy says 'Rrrruff!'