Java語言特性系列
這是Java語言特性系列的第一篇,從java5的新特性開始講起。初衷就是能夠方便的查看語言的演進歷史。html
所謂類型擦除指的就是Java源碼中的範型信息只容許停留在編譯前期,而編譯後的字節碼文件中將再也不保留任何的範型信息。也就是說,範型信息在編譯時將會被所有刪除,其中範型類型的類型參數則會被替換爲Object類型,並在實際使用時強制轉換爲指定的目標數據類型。而C++中的模板則會在編譯時將模板類型中的類型參數根據所傳遞的指定數據類型生成相對應的目標代碼。java
Map<Integer, Integer> squares = new HashMap<Integer, Integer>();
public void printList(List<?> list, PrintStream out) throws IOException { for (Iterator<?> i = list.iterator(); i.hasNext(); ) { out.println(i.next().toString()); } }
public static <A extends Number> double sum(Box<A> box1,Box<A> box2){ double total = 0; for (Iterator<A> i = box1.contents.iterator(); i.hasNext(); ) { total = total + i.next().doubleValue(); } for (Iterator<A> i = box2.contents.iterator(); i.hasNext(); ) { total = total + i.next().doubleValue(); } return total; }
public void testEnumMap(PrintStream out) throws IOException { // Create a map with the key and a String message EnumMap<AntStatus, String> antMessages = new EnumMap<AntStatus, String>(AntStatus.class); // Initialize the map antMessages.put(AntStatus.INITIALIZING, "Initializing Ant..."); antMessages.put(AntStatus.COMPILING, "Compiling Java classes..."); antMessages.put(AntStatus.COPYING, "Copying files..."); antMessages.put(AntStatus.JARRING, "JARring up files..."); antMessages.put(AntStatus.ZIPPING, "ZIPping up files..."); antMessages.put(AntStatus.DONE, "Build complete."); antMessages.put(AntStatus.ERROR, "Error occurred."); // Iterate and print messages for (AntStatus status : AntStatus.values() ) { out.println("For status " + status + ", message is: " + antMessages.get(status)); } }
public String getDescription() { switch(this) { case ROSEWOOD: return "Rosewood back and sides"; case MAHOGANY: return "Mahogany back and sides"; case ZIRICOTE: return "Ziricote back and sides"; case SPRUCE: return "Sitka Spruce top"; case CEDAR: return "Wester Red Cedar top"; case AB_ROSETTE: return "Abalone rosette"; case AB_TOP_BORDER: return "Abalone top border"; case IL_DIAMONDS: return "Diamonds and squares fretboard inlay"; case IL_DOTS: return "Small dots fretboard inlay"; default: return "Unknown feature"; } }
將primitive類型轉換成對應的wrapper類型:Boolean、Byte、Short、Character、Integer、Long、Float、Doublesegmentfault
public static void m1(Integer i){ System.out.println("this is integer"); } public static void m1(double d){ System.out.println("this is double"); }
m1(1)輸出的是double,方法匹配時線下兼容,不考慮boxing與unboxing。安全
private String print(Object... values) { StringBuilder sb = new StringBuilder(); for (Object o : values) { sb.append(o.toString()) .append(" "); } return sb.toString(); }
@Documented @Inherited @Retention(RetentionPolicy.RUNTIME) public @interface InProgress { }
@Documented @Retention(RetentionPolicy.RUNTIME) @Target({ElementType.TYPE, ElementType.METHOD, ElementType.CONSTRUCTOR, ElementType.ANNOTATION_TYPE}) public @interface TODO { String value(); }
public enum ElementType { /** Class, interface (including annotation type), or enum declaration */ TYPE, /** Field declaration (includes enum constants) */ FIELD, /** Method declaration */ METHOD, /** Parameter declaration */ PARAMETER, /** Constructor declaration */ CONSTRUCTOR, /** Local variable declaration */ LOCAL_VARIABLE, /** Annotation type declaration */ ANNOTATION_TYPE, /** Package declaration */ PACKAGE }
public enum RetentionPolicy { /** * Annotations are to be discarded by the compiler. */ SOURCE, /** * Annotations are to be recorded in the class file by the compiler * but need not be retained by the VM at run time. This is the default * behavior. */ CLASS, /** * Annotations are to be recorded in the class file by the compiler and * retained by the VM at run time, so they may be read reflectively. * * @see java.lang.reflect.AnnotatedElement */ RUNTIME }
public class ReflectionTester { public ReflectionTester() { } public void testAnnotationPresent(PrintStream out) throws IOException { Class c = Super.class; boolean inProgress = c.isAnnotationPresent(InProgress.class); if (inProgress) { out.println("Super is In Progress"); } else { out.println("Super is not In Progress"); } } public void testInheritedAnnotation(PrintStream out) throws IOException { Class c = Sub.class; boolean inProgress = c.isAnnotationPresent(InProgress.class); if (inProgress) { out.println("Sub is In Progress"); } else { out.println("Sub is not In Progress"); } } public void testGetAnnotation(PrintStream out) throws IOException, NoSuchMethodException { Class c = AnnotationTester.class; AnnotatedElement element = c.getMethod("calculateInterest", float.class, float.class); GroupTODO groupTodo = element.getAnnotation(GroupTODO.class); String assignedTo = groupTodo.assignedTo(); out.println("TODO Item on Annotation Tester is assigned to: '" + assignedTo + "'"); } public void printAnnotations(AnnotatedElement e, PrintStream out) throws IOException { out.printf("Printing annotations for '%s'%n%n", e.toString()); Annotation[] annotations = e.getAnnotations(); for (Annotation a : annotations) { out.printf(" * Annotation '%s' found%n", a.annotationType().getName()); } } public static void main(String[] args) { try { ReflectionTester tester = new ReflectionTester(); tester.testAnnotationPresent(System.out); tester.testInheritedAnnotation(System.out); tester.testGetAnnotation(System.out); Class c = AnnotationTester.class; AnnotatedElement element = c.getMethod("calculateInterest", float.class, float.class); tester.printAnnotations(element, System.out); } catch (Exception e) { e.printStackTrace(); } } }
for/in循環辦不到的事情:
(1)遍歷同時獲取index
(2)集合逗號拼接時去掉最後一個
(3)遍歷的同時刪除元素數據結構
import static java.lang.System.err; import static java.lang.System.out; import java.io.IOException; import java.io.PrintStream; public class StaticImporter { public static void writeError(PrintStream err, String msg) throws IOException { // Note that err in the parameter list overshadows the imported err err.println(msg); } public static void main(String[] args) { if (args.length < 2) { err.println( "Incorrect usage: java com.oreilly.tiger.ch08 [arg1] [arg2]"); return; } out.println("Good morning, " + args[0]); out.println("Have a " + args[1] + " day!"); try { writeError(System.out, "Error occurred."); } catch (IOException e) { e.printStackTrace(); } } }
/** * java.text.DateFormat * java.text.SimpleDateFormat * java.text.MessageFormat * java.text.NumberFormat * java.text.ChoiceFormat * java.text.DecimalFormat */ public class FormatTester { public static void printf() { //printf String filename = "this is a file"; try { File file = new File(filename); FileReader fileReader = new FileReader(file); BufferedReader reader = new BufferedReader(fileReader); String line; int i = 1; while ((line = reader.readLine()) != null) { System.out.printf("Line %d: %s%n", i++, line); } } catch (Exception e) { System.err.printf("Unable to open file named '%s': %s", filename, e.getMessage()); } } public static void stringFormat() { // Format a string containing a date. Calendar c = new GregorianCalendar(1995, MAY, 23); String s = String.format("Duke's Birthday: %1$tm %1$te,%1$tY", c); // -> s == "Duke's Birthday: May 23, 1995" System.out.println(s); } public static void formatter() { StringBuilder sb = new StringBuilder(); // Send all output to the Appendable object sb Formatter formatter = new Formatter(sb, Locale.US); // Explicit argument indices may be used to re-order output. formatter.format("%4$2s %3$2s %2$2s %1$2s", "a", "b", "c", "d"); // -> " d c b a" // Optional locale as the first argument can be used to get // locale-specific formatting of numbers. The precision and width can be // given to round and align the value. formatter.format(Locale.FRANCE, "e = %+10.4f", Math.E); // -> "e = +2,7183" // The '(' numeric flag may be used to format negative numbers with // parentheses rather than a minus sign. Group separators are // automatically inserted. formatter.format("Amount gained or lost since last statement: $ %(,.2f", 6217.58); // -> "Amount gained or lost since last statement: $ (6,217.58)" } public static void messageFormat() { String msg = "歡迎光臨,當前({0})等待的業務受理的顧客有{1}位,請排號辦理業務!"; MessageFormat mf = new MessageFormat(msg); String fmsg = mf.format(new Object[]{new Date(), 35}); System.out.println(fmsg); } public static void dateFormat(){ String str = "2010-1-10 17:39:21"; SimpleDateFormat format = new SimpleDateFormat("yyyyMMddHHmmss"); try { System.out.println(format.format(format.parse(str))); } catch (ParseException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public static void main(String[] args) { formatter(); stringFormat(); messageFormat(); dateFormat(); printf(); } }
public class BubbleSortThread extends Thread { private int[] numbers; public BubbleSortThread(int[] numbers) { setName("Simple Thread"); setUncaughtExceptionHandler( new SimpleThreadExceptionHandler()); this.numbers = numbers; } public void run() { int index = numbers.length; boolean finished = false; while (!finished) { index--; finished = true; for (int i=0; i<index; i++) { // Create error condition if (numbers[i+1] < 0) { throw new IllegalArgumentException( "Cannot pass negative numbers into this thread!"); } if (numbers[i] > numbers[i+1]) { // swap int temp = numbers[i]; numbers[i] = numbers[i+1]; numbers[i+1] = temp; finished = false; } } } } } class SimpleThreadExceptionHandler implements Thread.UncaughtExceptionHandler { public void uncaughtException(Thread t, Throwable e) { System.err.printf("%s: %s at line %d of %s%n", t.getName(), e.toString(), e.getStackTrace()[0].getLineNumber(), e.getStackTrace()[0].getFileName()); } }
public class Producer extends Thread { private BlockingQueue q; private PrintStream out; public Producer(BlockingQueue q, PrintStream out) { setName("Producer"); this.q = q; this.out = out; } public void run() { try { while (true) { q.put(produce()); } } catch (InterruptedException e) { out.printf("%s interrupted: %s", getName(), e.getMessage()); } } private String produce() { while (true) { double r = Math.random(); // Only goes forward 1/10 of the time if ((r*100) < 10) { String s = String.format("Inserted at %tc", new Date()); return s; } } } }
著名的JUC類庫。oracle
Arrays.sort(myArray); Arrays.toString(myArray) Arrays.binarySearch(myArray, 98) Arrays.deepToString(ticTacToe) Arrays.deepEquals(ticTacToe, ticTacToe3)
避開集合的add/remove操做,使用offer、poll操做(不拋異常)app
Queue q = new LinkedList(); 採用它來實現queue
支持協變返回框架
線程不安全,在單線程下替換string buffer提升性能dom