2014年4月22日 星期二

【File I / O 處理 09】位元組:BufferedOutputStream 類別


import java.io.*;
import java.util.Scanner;


public class FileIOBufferedOutputStream {

 public static void main(String[] args) {
  try {
   String fileName, fileDir;
   
   System.out.println("請輸入檔名: ");
   Scanner sn = new Scanner(System.in);
   fileDir = sn.next();
   
   BufferedOutputStream of = new BufferedOutputStream(new FileOutputStream(fileDir));
   String str = "Hello World!";
   byte[] b = str.getBytes();
   for(int i = 0; i < b.length; i++)
    of.write(b[i]);
   of.close();
  } catch(IOException e){
   System.out.println("輸入檔案路徑錯誤");
  }
 }

}
執行結果










新增檔案

【File I / O 處理 08】位元組:OutputStream 類別


import java.io.*;
import java.util.Scanner;


public class FileIOOutputStream {

 public static void main(String[] args) {
  String fileName, fileDir;
  try{
   System.out.println("請輸入檔名: ");
   Scanner sn = new Scanner(System.in);
   fileDir = sn.next();
   
   FileOutputStream of = new FileOutputStream(fileDir);
   String str = "Hello World!";
   byte[] b = str.getBytes();
   for(int i=0; i < b.length; i++)
    of.write(b[i]);
   of.close(); 
  }catch (IOException e){
   System.out.println("輸入檔案路徑錯誤");
  }
  
 }

}
執行結果












新增檔案

【File I / O 處理 07】位元組:FileInputStream 類別

輸入的來源是檔案。
import java.io.*;
import java.util.Scanner;


public class FileIOFileInputStream {

 public static void main(String[] args) {
  try{
   String fileName, fileDir;
   
   System.out.println("請輸入檔名: ");
   Scanner sn = new Scanner(System.in);
   fileDir = sn.next();

   FileInputStream fin = new FileInputStream(fileDir);
   int size = fin.available();
   byte[] b = new byte[size];
   fin.read(b);
   System.out.println(fileDir + " 位元大小: "+ size);
   for(int i=0; i < size;i++ ){
    //System.out.println(Byte.toString(b[i]));
    //System.out.format("%c", b[i]);
    System.out.print((char)b[i]);
   }
   System.out.println("OK");
   fin.close();
  }catch(IOException e){
   System.out.println("輸入檔案路徑錯誤");
  }
 }

}

執行結果










原本檔案內容

【File I / O 處理 06】BufferedWriter 類別


import java.io.*;
import java.util.Scanner;

public class FileIOBufferedWriter {

 public static void main(String[] args) {
  try {
   String fileName, fileDir;
   
   System.out.println("請輸入檔名: ");
   Scanner sn = new Scanner(System.in);
   fileDir = sn.next();
   
   BufferedWriter of = new BufferedWriter(new FileWriter (fileDir));
            of.write("以 BufferedWriter 寫入測試");
            of.newLine();
            of.write("讀取顯示這檔案");
            of.newLine();
            of.close();
            System.out.println("完成寫入檔案: "+ fileDir);
  }catch(IOException e){
   System.out.println("輸入檔案路徑錯誤");
   
  }
 }

}

執行結果









檢視輸出檔案









以此方式寫入,每次執行都會清除原來檔案的內容,若要在原檔案附加內容時,需要更改 FileWriter的參數:

      BufferedWriter of = new BufferedWriter(new FileWriter (fileDir, true));

【File I / O 處理 05-00】檔案寫入類別

Writer 類別處理字元資料流寫入指定檔案,其類別繼承圖示如下

【File I / O 處理 03】FileReader, BufferedReader 類別

import java.io.*; import java.util.Scanner;

public class FileIOBufferReader {

 public static void main(String[] args) {
  try {
   String fileName, fileDir;
   
   System.out.println("請輸入檔名: ");
   Scanner sn = new Scanner(System.in);
   fileDir = sn.next();
   
   FileReader file = new FileReader(fileDir);
   BufferedReader bf = new BufferedReader(file);
   do {
    String data = bf.readLine();
    if (data == null)
     break;
    System.out.println(data);
   } while (true);
   
   bf.close();
   
  } catch (IOException e){
   System.out.println("輸入檔案路徑錯誤");
  }
 }

}

執行結果

I/O : File 類別

 
import java.io.File;
import java.util.Scanner;

public class FileTest {
 public static void main(String[] args) {
  String filePath, fileName;
  
  System.out.print("檔案名稱 ? ");
  Scanner sn = new Scanner(System.in);
  filePath = sn.next();
  File fin = new File(filePath);
  fileName = fin.getName();
  
  if (fin.isFile())
   System.out.println("File exists : " + fileName);
  else if (fin.isDirectory())
   System.out.println("Directory exists : " + fileName);
  else {
   System.out.println("File or Directory Not Found");
   System.exit(0);
  }
 }
}

執行結果













測試有目錄存在時

【File I / O 處理 01】File 處理

File 類別並不是 I/O 中所定義在資料流處理的類別,但它可直接處理檔案 file 及檔案系統 (file system,即知道檔案在那個目錄 directory 之下)。
   方法                 功能
   _____________________________________________

 canRead             比較可否讀取檔案
   canWrite            比較可否寫入檔案
   compareTo           比較 2 個檔案路徑
   createNewFile       建新檔案
   createTempFile      建臨時檔案
   delete              刪除檔案路徑
   exists              判斷檔案存在否
   getName             取出檔案或路徑名稱
   isDirectory         判斷File物件是否為目錄
   length              檔案長度
   list                取出File名稱,以字串陣列表示
   renameTo            更改檔名
   setReadOnly         將檔案 / 目錄設定唯讀
   toString            取出檔案路徑字串
   toURL               將檔案路徑轉換成 URL 檔案
   _____________________________________________
   

檔案:FileIOIsFile.java
import java.io.File;
import java.util.Scanner;


public class FileIOIsFile {

 public static void main(String[] args) {
  String fileName, fileDir;
  
  System.out.println("請輸入檔名: ");
  Scanner sn = new Scanner(System.in);
  fileDir = sn.next();
  
  File file = new File(fileDir);
  if(file.isFile())
   System.out.println(file.getName()+" 是檔案");
  else if(file.isDirectory())
   System.out.println(file.getName()+" 是目錄");
  else {
   System.out.println("無此檔案或目錄");
   System.exit(0);
  }
 }

}
執行結果

輸入檔案名稱









輸入目錄名稱



【JDBC 01】下載 JDBC Driver,並連接 DB


import java.sql.*;

public class DBConn2 {

 public static void main(String[] args) {
  
  try {
   Class.forName("com.mysql.jdbc.Driver");
   System.out.println("Success loading JDBC-ODBC Bridge Driver");
  } catch (ClassNotFoundException e){
   System.out.println("JDBC 沒有驅動程式" + e.getMessage()); 
  }
  
  try { 
   
      String url =  "jdbc:mysql://localhost:3306/phone?" + 
                    "user=root&password=12345"; 
      Connection conn = DriverManager.getConnection(url); 
      if(!conn.isClosed()) 
          System.out.println("資料庫連線成功"); 

      conn.close(); 
  } 
  catch(SQLException e) { 
   System.out.println("資料庫連線失敗");
  }
 }

}


執行結果

【JDBC 00】安裝 XAMPP,JDBC Driver

1. 下載,並安裝 XAMPP: https://www.apachefriends.org/zh_tw/index.html
2. 下載 JDBC Driver,並加入 Project 的 Build Path 中 : https://dev.mysql.com/downloads/connector/j/
3. 設定 XAMPP 安全權限
 注意: 下列一定要設成 no,否則以 DriverManager.getConnection(url) 時,資料庫無法連接成功 

XAMPP:  MySQL is accessable via network. 
XAMPP: Normaly that's not recommended. Do you want me to turn it off? [yes] no



ElvisdeMacBook-Pro:~ root# whoami
root
ElvisdeMacBook-Pro:~ root# /Applications/XAMPP/xamppfiles/xampp security
XAMPP:  Quick security check...
XAMPP:  Your XAMPP pages are NOT secured by a password. 
XAMPP: Do you want to set a password? [yes] 
XAMPP: Password: 
XAMPP: Password (again): 
XAMPP:  Password protection active. Please use 'xampp' as user name!
XAMPP:  MySQL is accessable via network. 
XAMPP: Normaly that's not recommended. Do you want me to turn it off? [yes] no
XAMPP:  The MySQL/phpMyAdmin user pma has no password set!!! 
XAMPP: Do you want to set a password? [yes] 
XAMPP: Password: 
XAMPP: Password (again): 
XAMPP:  Setting new MySQL pma password.
XAMPP:  Setting phpMyAdmin's pma password to the new one.
XAMPP:  MySQL has no root passwort set!!! 
XAMPP: Do you want to set a password? [yes] 
XAMPP:  Write the password somewhere down to make sure you won't forget it!!! 
XAMPP: Password: 
XAMPP: Password (again): 
XAMPP:  Setting new MySQL root password.

【JDBC 00】建立資料庫

DB 操作:

查詢: show databases;
新增: create database Database_Name;
刪除: drop database Database_Name;
開啓: use Database_Name;

Table 操作:

新增: create table Table_Name ( ... );
查詢全部: show tables;
刪除: drop table Table_Name;

Schema :

查詢表格: show columns from Table_Name;

Data:

新增: insert into Table_Name(no,name) values (1,'Tom');


以 root 帳號登入
ElvisdeMacBook-Pro:bin elvismeng$ pwd
/Applications/XAMPP/bin
ElvisdeMacBook-Pro:bin elvismeng$ ./mysql -u root -p
Enter password: 
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 56
Server version: 5.6.16 Source distribution

Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

mysql> 

新增資料庫
mysql> CREATE DATABASE phone;
Query OK, 1 row affected (0.01 sec)

mysql>

開啟資料庫
mysql> use phone;
Database changed
mysql> 

新增資料表 Table

mysql> CREATE TABLE student (
    -> ID integer,
    -> name char(30)
    -> );
Query OK, 0 rows affected (0.07 sec)

mysql>

查詢資料庫所有資料表 Table
mysql> show tables;
+-----------------+
| Tables_in_phone |
+-----------------+
| student         |
+-----------------+
1 row in set (0.00 sec)

mysql> 

查詢指定的資料表 Table
mysql> SHOW COLUMNS FROM student;
+-------+----------+------+-----+---------+-------+
| Field | Type     | Null | Key | Default | Extra |
+-------+----------+------+-----+---------+-------+
| ID    | int(11)  | YES  |     | NULL    |       |
| name  | char(30) | YES  |     | NULL    |       |
+-------+----------+------+-----+---------+-------+
2 rows in set (0.01 sec)

mysql> 

新增資料 Table
mysql> INSERT INTO student (ID, name) values (1,'Tom');
Query OK, 1 row affected (0.01 sec)

mysql> INSERT INTO student (ID, name) values (2,'Bob');
Query OK, 1 row affected (0.01 sec)

mysql> INSERT INTO student (ID, name) values (3,'Joe');
Query OK, 1 row affected (0.01 sec)

mysql> 

查詢輸入資料 Table
mysql> SELECT * FROM student;
+------+------+
| ID   | name |
+------+------+
|    1 | Tom  |
|    2 | Bob  |
|    3 | Joe  |
+------+------+
3 rows in set (0.01 sec)

mysql> 

Reference:
http://bonny.com.tw/web/xampp/0603newmysql.htm

【JDBC 03】異動資料:新㽪、修改、刪除


import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;

import javax.swing.JOptionPane;

import com.mysql.jdbc.Statement;


public class DBConn4 {

 public static void main(String[] args) {
  try {
   Class.forName("com.mysql.jdbc.Driver");
   System.out.println("Success loading JDBC-ODBC Bridge Driver");
  } catch (ClassNotFoundException e){
   System.out.println("JDBC 沒有驅動程式" + e.getMessage()); 
  }
  
  int op = 0;
  String sqlstr ="",id="",name="";
  try {
   op = Integer.parseInt(JOptionPane.showInputDialog("請選擇選單\n1: 新增 2:修改 3:刪除"));
   
   switch(op){
   case 1:
    id = JOptionPane.showInputDialog("請輸入座號");
    name = JOptionPane.showInputDialog("請輸姓名").replace("'", "'");
    sqlstr = "INSERT INTO student(ID,name) VALUES (" +
              id  + ",'"+ name + "'" + ")";
    break;
   case 2:
    id = JOptionPane.showInputDialog("請輸入欲修改資料(以座號為依據)");
    name = JOptionPane.showInputDialog("請輸姓名").replace("'", "'");
    sqlstr = "UPDATE student SET name='" + name +"'" +
             "WHERE ID = "+ id;
    break;
   case 3:
    id = JOptionPane.showInputDialog("請輸入欲刪除資料(以座號為依據)");
    sqlstr = "DELETE FROM student WHERE ID="+id;
    break;
   default:
    System.out.println("Error");
   }
  }catch(NumberFormatException e){
   
  }
  
  
  try { 
   
      String url =  "jdbc:mysql://localhost:3306/phone?" + 
                    "user=root&password=12345"; 
      Connection conn = DriverManager.getConnection(url); 
      if(!conn.isClosed()) 
          System.out.println("資料庫連線成功"); 
      
      Statement sm = (Statement) conn.createStatement();
      if(op !=0){
       sm.execute(sqlstr);
      }
      
      ResultSet rs = sm.executeQuery("SELECT * FROM student");
      ResultSetMetaData rsmd = rs.getMetaData();
      for(int i=1; i <= rsmd.getColumnCount(); i++){
       System.out.print(rsmd.getColumnName(i)+"\t");
      }
      System.out.println("\n---------------------");
      while(rs.next()){
       System.out.print(rs.getInt(1) + "\t" +
                           rs.getString(2));
       System.out.println();
      }
      
            sm.close();
      conn.close(); 
  } 
  catch(SQLException e) { 
   System.out.println("資料庫連線失敗");
  }
 }

}


執行結果
新增
















修改
















刪除







【JDBC 02】查詢資料

import java.sql.*;

import com.mysql.jdbc.Statement;

public class DBConn3 {

 public static void main(String[] args) {
  
  try {
   Class.forName("com.mysql.jdbc.Driver");
   System.out.println("Success loading JDBC-ODBC Bridge Driver");
  } catch (ClassNotFoundException e){
   System.out.println("JDBC 沒有驅動程式" + e.getMessage()); 
  }
  
  try { 
   
      String url =  "jdbc:mysql://localhost:3306/phone?" + 
                    "user=root&password=12345"; 
      Connection conn = DriverManager.getConnection(url); 
      if(!conn.isClosed()) 
          System.out.println("資料庫連線成功"); 
      
      Statement sm = (Statement) conn.createStatement();
      ResultSet rs = sm.executeQuery("SELECT * FROM student");
      ResultSetMetaData rsmd = rs.getMetaData();
      for(int i=1; i <= rsmd.getColumnCount(); i++){
       System.out.print(rsmd.getColumnName(i)+"\t");
      }
      System.out.println("\n---------------------");
      while(rs.next()){
       System.out.print(rs.getInt(1) + "\t" +
                           rs.getString(2));
       System.out.println();
      }
      
            sm.close();
      conn.close(); 
  } 
  catch(SQLException e) { 
   System.out.println("資料庫連線失敗");
  }
 }

}

執行結果

2014年4月21日 星期一

【File I / O 處理 02】Reader 類別

Reader 類別處理字元資料流讀取。

    方法                      功能
   _______________________________________________________

    close()                  關閉資料流
    mark(int numChars)       在資料流中標示目前的位置
    read()                   讀取 1 個字元
    read(char[] buffer)      將讀取的字元陣列放在buffer陣列中
    ready()                  檢查資料流是否準備好讀取
    reset()                  重置資料流
    skip(long n)             跳過 n 個字元
   _______________________________________________________
    



import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.Scanner;


public class FileIOFileReader {

 public static void main(String[] args) {
  try{
   String fileName, fileDir;
   
   System.out.println("請輸入檔名: ");
   Scanner sn = new Scanner(System.in);
   fileDir = sn.next();
  
   char[] buffer = new char[100];
   FileReader file = new FileReader(fileDir);
   file.read(buffer);
   System.out.println(buffer);
   file.close();
  } catch (IOException e) {
   // TODO Auto-generated catch block
   System.out.println("輸入檔案路徑錯誤");
  }
  
 }

}
執行結果

2014年4月17日 星期四

練習 8

續練習7. 設計一個活期存款教易帳戶 UI, 畫面上有 Label 元件 (銀行帳號 , 存入金額) 以及 TextField, 另外有一個確認按鈕 Button, 按下時顯示"交易完成" http://download.eclipse.org/windowbuilder/WB/release/R201309271200/4.2/

Generics : 多個泛型類型

class GenericNumbers <T1,T2>{
 private T1 number1;
 private T2 number2;
 
 public void setNumber1(T1 number){
  this.number1 = number;
 }
 
 public T1 getNumber1(){
  return number1;
 }
 
 public void setNumber2(T2 number){
  this.number2 = number;
 }
 
 public T2 getNumber2(){
  return number2;
 }
}
public class GenericsMultiDefined {

 public static void main(String[] args) {
  GenericNumbers <Integer, Double> number = new GenericNumbers<Integer, Double> ();
  number.setNumber1(10);
  number.setNumber2(20.5);
  Double d = number.getNumber1() + number.getNumber2();
  System.out.println("total : "+d);
 }

}
執行結果

Generics : 限制泛型可用類型

class GenericNumber2 <T extends Integer>{
 T number;
 public void setNumber(T number){
  this.number = number;
 }
 
 public T getNumber(){
  return number;
 }
}
public class GenericsList {

 public static void main(String[] args) {
  GenericNumber2 <integer> i = new GenericNumber2 <integer>();
  i.setNumber(10);
  System.out.println("Number value : "+i.getNumber());

 }

}
執行結果







若資料型態想改用Double定義,例如: GenericNumber2 < Double > d = new GenericNumber2 < Double > (); 那麼在編譯時,就會指出下列錯誤
Exception in thread "main" java.lang.Error: Unresolved compilation problems: 
 Bound mismatch: The type Double is not a valid substitute for the bounded parameter  of the type GenericNumber2
 Bound mismatch: The type Double is not a valid substitute for the bounded parameter  of the type GenericNumber2

 at GenericsList.main(GenericsList.java:18)
另,定義泛型類別
public class GenericClass <T> {
 ...
}
就如同以下列方式定義
public class GenericClass <T extends Object > {
 ...
}

Generics : 單個泛型類型

定義類別 class 時,當幾個類別的邏輯其實都相同,但只有涉及的資料型態不同時,則以泛型來定義類別(Generics Class)。

泛型類別本身就是資料形態,可用來宣告物件。

使用時要注意轉換型態或介面 type casting,否則在執行時 run time 會發生 ClassCastException。

class GenericNumber <T>{
 private T number;
 
 public void setNumber(T number){
  this.number = number;
 }
 
 public T getNumber(){
  return number;
 }
}

public class GenericsUndefined {

 public static void main(String[] args) {
  GenericNumber <Integer> i = new GenericNumber <Integer>();
  i.setNumber(10);
  System.out.println("Integer value : " + i.getNumber());
  
  GenericNumber <Boolean> f = new GenericNumber <Boolean> ();
  f.setNumber(true);
  System.out.println("Boolean value : " + f.getNumber());
  
  GenericNumber <Double> d = new GenericNumber <Double> ();
  d.setNumber(10.5);
  System.out.println("Double value : " + d.getNumber());
  
 }
}
執行結果




以泛型類別方法寫程式時,若不同型別做指定, 例如 d = i ; 時,編譯會出現如下錯誤
Exception in thread "main" java.lang.Error: Unresolved compilation problem: 
 Type mismatch: cannot convert from GenericNumber to GenericNumber

 at GenericsUndefined.main(GenericsUndefined.java:28)

Generics : 擴充泛型類別、實作泛型介面


class GenericNumber5 < T1,T2 >{
 private T1 number1;
 private T2 number2;
 
 public void setNumber1 (T1 number){
  this.number1 = number;
 }
 
 public T1 getNumber1 (){
  return number1;
 }
 
 public void setNumber2 (T2 number){
  this.number2 = number;
 }
 
 public T2 getNumber2 (){
  return number2;
 }
}

class SubGenericNumber5 < T1, T2, T3 > extends GenericNumber5 < T1, T2 > {
 private T3 number3;
 
 public void setNumber3 (T3 number){
  this.number3 = number;
 }
 
 public T3 getNumber3 (){
  return number3;
 }

}

public class GenericsCustomized {
 
 public static void main(String[] args) {
  SubGenericNumber5 < Integer, Long,Double> num = new SubGenericNumber5 <Integer, Long,Double&gr;();
  num.setNumber1(10);
  num.setNumber2( 200L );
  num.setNumber3(300.5);
  Double d = num.getNumber1() + num.getNumber2() + num.getNumber3();
  System.out.println("Total : "+d);
 
 }

}


執行結果
若要使用父類別時,父類別上宣告的型態持有者數目在繼承下來時,必須全寫。例如:SubGenericNumber 定義為 class SubGenericNumber5 extends GenericNumber5 ,則會發生編譯錯誤
Exception in thread "main" java.lang.Error: Unresolved compilation problems: 
 Incorrect number of arguments for type SubGenericNumber5; it cannot be parameterized with arguments 
 Incorrect number of arguments for type SubGenericNumber5; it cannot be parameterized with arguments 

 at GenericsCustomized.main(GenericsCustomized.java:38)
但,若子類別不用到父類別定義的資料、方法時,則可改寫如下。不過,建議將父親類別的型態持有者都保留。
class GenericNumber5 <T1,T2>{
 private T1 number1;
 private T2 number2;
 
 public void setNumber1 (T1 number){
  this.number1 = number;
 }
 
 public T1 getNumber1 (){
  return number1;
 }
 
 public void setNumber2 (T2 number){
  this.number2 = number;
 }
 
 public T2 getNumber2 (){
  return number2;
 }
}

class SubGenericNumber5 <T3> extends GenericNumber5 {
 private T3 number3;
 
 public void setNumber3 (T3 number){
  this.number3 = number;
 }
 
 public T3 getNumber3 (){
  return number3;
 }

}

public class GenericsCustomized {
 
 public static void main(String[] args) {

  SubGenericNumber5 <Double> num = new SubGenericNumber5 <Double>();
  num.setNumber3(300.5);
  Double d = num.getNumber3();
  System.out.println("Total : "+d);
  
 
 }

}
執行結果

集合 Collection:概述

集合 Collection:與陣列Array有點類似,處理一群相關性的資料(或稱“元素”)。這些資料以Java 提供的工具箱 Collections 類別來處理,此工具箱包含 Hashtable、TreeSet、ArrayList、LinkedList、HashMap、TreeMap 等。




















集合物件的特性

集合界面 具體實作類別 排序性 循序性 唯一性 鍵值對應
Set HashSet
SortedSet TreeSet
List ArrayList, LinkedList
Map HashMap
SortedMap TreeMap

參考


1. How are the collections structured? Which one should I choose?