17.1 完整的容器分类法
17.2 填充容器
这一小节,简单的介绍了java.util.Collections中的两个方法:
public static <T> List<T> nCopies(int n,T o)
public static <T> void fill(List<? super T> list,T obj)
这两个方法可以多次拷贝同一个对象到一个列表中
java代码:
//The Collections.fill() & Collections.nCopies() methods. package containers; import java.util.ArrayList; import java.util.Collections; import java.util.List; class StringAddress { private String s; public StringAddress(String s) { this.s = s; } @Override public String toString() { return super.toString() + " " + s; } } public class FillingLists { public static void main(String[] args) { List<StringAddress> list = new ArrayList<StringAddress>( Collections.nCopies(4, new StringAddress("Hello"))); System.out.println(list); Collections.fill(list, new StringAddress("World")); System.out.println(list); } }
运行结果:
[containers.StringAddress@4e81d783 Hello, containers.StringAddress@4e81d783 Hello, containers.StringAddress@4e81d783 Hello, containers.StringAddress@4e81d783 Hello] [containers.StringAddress@2e6c01b9 World, containers.StringAddress@2e6c01b9 World, containers.StringAddress@2e6c01b9 World, containers.StringAddress@2e6c01b9 World]
A Generator solution
package net.mindview.util; import java.util.ArrayList; /** * 该类本身就是一个ArrayList,把Generator生成器生成的对象添加到该类中 * list方法返回一个CollectionData对象 */ public class CollectionData<T> extends ArrayList<T> { public CollectionData(Generator<T> gen, int quantity) { for (int i = 0; i < quantity; i++) { add(gen.next()); } } // A generic convenience method: public static <T> CollectionData<T> list(Generator<T> gen, int quantity) { return new CollectionData<T>(gen, quantity); } }
把生成器对象转换称Collection
测试代码:
package containers; import java.util.LinkedHashSet; import java.util.Set; import net.mindview.util.CollectionData; import net.mindview.util.Generator; class Government implements Generator<String>{ String[] foundation = ("strange women lying in ponds " + "distributing swords is no basis for a system of " + "government").split(" "); private int index; @Override public String next() { return foundation[index++]; } } public class CollectionDataTest { public static void main(String[] args) { Set<String> set = new LinkedHashSet<>( new CollectionData<>(new Government(), 15)); //Using the convenience method set.addAll(CollectionData.list(new Government(), 15)); System.out.println(set); } }
package containers; import java.util.ArrayList; import java.util.HashSet; import net.mindview.util.CollectionData; import net.mindview.util.RandomGenerator; public class CollectionDataGeneration { public static void main(String[] args) { System.out.println(new ArrayList<String>( CollectionData.list(//Convenience method new RandomGenerator.String(9),10))); System.out.println(new HashSet<Integer>( new CollectionData<Integer>( new RandomGenerator.Integer(),10))); } }
在实验的过程中需要用的其他类:
//: net/mindview/util/Generator.java // A generic interface. package net.mindview.util; public interface Generator<T> { T next(); } ///:~
//: net/mindview/util/CountingGenerator.java // Simple generator implementations. package net.mindview.util; public class CountingGenerator { public static class Boolean implements Generator<java.lang.Boolean> { private boolean value = false; public java.lang.Boolean next() { value = !value; // Just flips back and forth return value; } } public static class Byte implements Generator<java.lang.Byte> { private byte value = 0; public java.lang.Byte next() { return value++; } } static char[] chars = ("abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ").toCharArray(); public static class Character implements Generator<java.lang.Character> { int index = -1; public java.lang.Character next() { index = (index + 1) % chars.length; return chars[index]; } } public static class String implements Generator<java.lang.String> { private int length = 7; Generator<java.lang.Character> cg = new Character(); public String() {} public String(int length) { this.length = length; } public java.lang.String next() { char[] buf = new char[length]; for(int i = 0; i < length; i++) buf[i] = cg.next(); return new java.lang.String(buf); } } public static class Short implements Generator<java.lang.Short> { private short value = 0; public java.lang.Short next() { return value++; } } public static class Integer implements Generator<java.lang.Integer> { private int value = 0; public java.lang.Integer next() { return value++; } } public static class Long implements Generator<java.lang.Long> { private long value = 0; public java.lang.Long next() { return value++; } } public static class Float implements Generator<java.lang.Float> { private float value = 0; public java.lang.Float next() { float result = value; value += 1.0; return result; } } public static class Double implements Generator<java.lang.Double> { private double value = 0.0; public java.lang.Double next() { double result = value; value += 1.0; return result; } } } ///:~
//: net/mindview/util/RandomGenerator.java // Generators that produce random values. package net.mindview.util; import java.util.*; public class RandomGenerator { private static Random r = new Random(47); public static class Boolean implements Generator<java.lang.Boolean> { public java.lang.Boolean next() { return r.nextBoolean(); } } public static class Byte implements Generator<java.lang.Byte> { public java.lang.Byte next() { return (byte)r.nextInt(); } } public static class Character implements Generator<java.lang.Character> { public java.lang.Character next() { return CountingGenerator.chars[ r.nextInt(CountingGenerator.chars.length)]; } } public static class String extends CountingGenerator.String { // Plug in the random Character generator: { cg = new Character(); } // Instance initializer public String() {} public String(int length) { super(length); } } public static class Short implements Generator<java.lang.Short> { public java.lang.Short next() { return (short)r.nextInt(); } } public static class Integer implements Generator<java.lang.Integer> { private int mod = 10000; public Integer() {} public Integer(int modulo) { mod = modulo; } public java.lang.Integer next() { return r.nextInt(mod); } } public static class Long implements Generator<java.lang.Long> { private int mod = 10000; public Long() {} public Long(int modulo) { mod = modulo; } public java.lang.Long next() { return new java.lang.Long(r.nextInt(mod)); } } public static class Float implements Generator<java.lang.Float> { public java.lang.Float next() { // Trim all but the first two decimal places: int trimmed = Math.round(r.nextFloat() * 100); return ((float)trimmed) / 100; } } public static class Double implements Generator<java.lang.Double> { public java.lang.Double next() { long trimmed = Math.round(r.nextDouble() * 100); return ((double)trimmed) / 100; } } } ///:~