Extend a Java ArrayList

I want to extend ArrayList to add several methods for a specific class, and its examples will be saved by the extended ArrayList The following simplified description code example

This seems wise to me, but I am very new to Java. I see other problems that do not encourage extending ArrayList, such as extending ArrayList and creating new methods I didn't know there was enough java to understand objections

In my previous attempts, I finally created some methods basically passed to ArrayList in thingcontainer, so it seems easier to expand

Is there a better way to do what I want to do? If so, how should it be implemented?

import java.util.*;

class Thing {
    public String name;
    public int amt;

    public Thing(String name,int amt) {
        this.name = name;
        this.amt = amt;
    }

    public String toString() {
        return String.format("%s: %d",name,amt);
    }

    public int getAmt() {
        return amt;
    }
}

class ThingContainer extends ArrayList<Thing> {
    public void report() {
        for(int i=0; i < size(); i++) {
            System.out.println(get(i));
        }
    }

    public int total() {
        int tot = 0;
        for(int i=0; i < size(); i++) {
            tot += ((Thing)get(i)).getAmt();
        }
        return tot;
    }

}

public class Tester {
    public static void main(String[] args) {
        ThingContainer blue = new ThingContainer();

        Thing a = new Thing("A",2);
        Thing b = new Thing("B",4);

        blue.add(a);
        blue.add(b);

        blue.report();
        System.out.println(blue.total());

        for (Thing tc: blue) {
            System.out.println(tc);
        }
    }
}

Solution

Nothing in that answer discourages extending ArrayList; There is a grammatical problem Class extensions exist, so we can reuse the code

The normal objection to extending a class is the "favor composition over inheritance" discussion Extension is not always the preferred mechanism, but it depends on what you are doing

Edit the combination example on request

public class ThingContainer implements List<Thing> { // Or Collection based on your needs.
    List<Thing> things;
    public boolean add(Thing thing) { things.add(thing); }
    public void clear() { things.clear(); }
    public Iterator<Thing> iterator() { things.iterator(); }
    // Etc.,and create the list in the constructor
}

You don't have to expose a complete list interface, just collect, or not at all Although there is no display function, it greatly reduces the general usefulness

In groovy, you can use the @ delegate annotation to automatically build methods Java can use the @ delegate annotation of project Lombok to do the same I don't know how Longmu Island exposes the interface, or if it

I use glowcoder, and in this case, I don't see any fundamental errors in the extension - it's really a problem to solve

Edit details about how inheritance violates encapsulation

For details, see Bloch's valid Java, item 16

If a subclass depends on the superclass behavior and the superclass behavior changes, the subclass may be interrupted This can be bad if we don't control superclasses

This is a specific example, removed from the book (sorry, Josh!), Pseudo code, and a lot of interpretation (all errors are mine)

class CountingHashSet extends HashSet {
    private int count = 0;
    boolean add(Object o) {
        count++;
        return super.add(o);
    }
    boolean addAll(Collection c) {
        count += c.size();
        return super.addAll(c);
    }
    int getCount() { return count; }
}

Then we use it:

s = new CountingHashSet();
s.addAll(Arrays.asList("bar","baz","plugh");

It returns... Three? no Vi Why?

HashSet. Addall() in HashSet Add (), but this is an internal implementation detail Our subclass addall () adds three and calls super Addall(), which calls add(), also increases count

We can delete addall () of the subclass, but now we rely on the implementation details of the superclass, which may change We can modify our addall () to iterate and call add () on each element, but now we are re implementing the superclass behavior. If the superclass behavior depends on access to private members, their purpose will fail and may not always be possible

Or a superclass can implement a new method, but our subclass will not, which means that users of our class may inadvertently bypass the expected behavior by directly calling the superclass method, so we must track the superclass API to determine when and if the subclass should change

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>