プログラミング第三 第1部 オブジェクト指向・Java復習 Java API 入出力 : java.io パッケージ GUI : java.awt, javax.swing パッケージ Javaの入出力:java.ioパッケージ ファイル、通信接続先、メモリ領域などへの 入出力を汎用的に行なうクラス集合 ポイント:連続するデータ(Stream) として抽象化 重要なクラス InputStream, OutputStream Byte Streamを表現する抽象クラス Byte単位での読み書きを行う Reader, Writer Character Streamとして入出力を扱う 文字単位での入出力処理を表現する抽象クラス 3 1 Byte Streamを表現するクラス 例: InputStreamの子クラス:Byte単位入力 ( InputStream ) ファイルシステムから rawデータを読み込み FileInputStream メモリ上のデータ列用 ByteArrayInputStream スレッド間通信用 PipedInputStream 直列化されたオブジェクト を読み込む ObjectInputStream ( FilterInputStream ) DataInputStream InputStreamに 拡張機能を提供 する BufferedInputStream PushbackInputStream OS非依存で プリミティブ型 を読込む拡張 バッファ機能拡張 読み戻し機能拡張 4 InputStream/OutputStreamの主なメソッド InputStreamの主なメソッド int read (); 入力ストリームから b.lengthバイト読み, bに格納 入力ストリームから次 のnバイトを読み飛ばす void close (); 入力ストリームを閉じ て,後始末 void write (int b); 出力ストリームにバイ ト列bを書く void flush (); 出力ストリームにバイ ト値bを書く void write (byte[] b); long skip (long n); 入力ストリームから次 のバイトを読む int read (byte[] b); OutputStreamの主なメソッド 出力ストリームをフラ ッシュ void close (); 出力ストリームを閉じ て,後始末 5 2 文字単位での入出力処理を表現するクラス 例: Readerの子クラス:文字単位入力 ( Reader ) ファイルシステム FileReader 文字列用 StringReader PipedReader スレッド間通信用 InputStreamReader InputStreamからの変換を行う. バイトを読み込み、指定された charset を使用して文字に変換する ( FilterReader ) バッファ機能拡張 BufferedReader 読み戻し機能拡張 PushbackReader 6 Reader/Writerの主なメソッド Readerの主なメソッド int read (); 入力ストリームから c.length個文字読み, cに格納 long skip (long n); 入力ストリームから次のn 文字を読み飛ばす void close (); 入力ストリームから次の 文字を読む int read (char[] c); Writerの主なメソッド 入力ストリームを閉じて ,後始末 void write (int c); void write (char[] c); 出力ストリームに文字列s を書く void flush (); 出力ストリームに文字の 配列cを書く void write (String s); 出力ストリームにcで指定 された文字 を書く 出力ストリームをフラッ シュ void close (); 出力ストリームを閉じて ,後始末 7 3 コード例:ファイルの読み書き import java.io.*; 簡略化のため 例外処理はしていない class TestIO{ public static void main(String[] args) throws IOException{ InputStream is; OutputStream os; ファイル名を引数にすると ___________ is = new FileInputStream(args[0]); os = new FileOutputStream(args[1]); ______ Pass.pass(is, os); の派生クラス byte[] b= {72,101,108,108,111,33,33,10}; % java TestIO ./TestIO.java ./text.txt is = new ByteArrayInputStream(b); Hello!! os = System.out; %cat ./text.txt Pass.pass(is, os); SystemクラスのStatic変数out Import java.io.*; } } その実体は_____________を …. 継承した______________ (以下省略) class Pass{ public static void pass(InputStream is, OutputStream os) throws IOException{ int c; while((c=is.read())!= -1){ os.write(c); ___判定 基底クラスを引数にする } } ことで____がある! _byteずつ読む 8 } 機能拡張:バッファリング BufferedInputStream, BufferedOutputStream バッファリングで入出力の効率を向上. 例:8MBのファイルの読み込み. FileInputStream=21秒.BufferedInputStream=1.6秒. 利用方法 他のストリームを引数で渡し内部に保持 InputStream is = new FileInputStream(“foo.txt”); InputStream is = new BufferedInputStream(new FileInputStream("foo.txt")); 10 4 機能拡張:StreamReader/Writer Javaプログラム 中文字 PrintWriter OutputStreamWriter OutputStream ファイル中 のデータ char c = 'a'; Unicode (2バイト) 'a' InputStream InputStreamReader BufferedReader ASCII, JIS, EUC-JP, SJIS, ISO-8299-1,... (1バイト以上) 11 機能拡張:StreamReader/Writer class Pass2{ public static void pass(InputStream is, OutputStream os) throws IOException{ int counter=0; int c; while((c=is.read())!= -1){ if(counter==5){ break; } os.write(c); counter++; 5_____ 読み書き } os.flush(); } } class Pass3{ public static void pass(InputStream is, OutputStream os) throws IOException{ int counter=0; int c; Reader r = new InputStreamReader(is); Writer w = new OutputStreamWriter(os); while((c=r.read())!= -1){ if(counter==5){ break; } w.write(c); 5_____読み書き counter++; } w.flush(); } } TestIOの中のPassをPass2やPass3に置き換えて実行すると…. %cat a.txt こんにちは、世界 %java TestIO a.txt b.txt %cat a.txt こんにちは、世界 %java TestIO a.txt b.txt %cat b.txt %cat b.txt 13 5 機能追加:書式機能 (PrintWriter) Writerに print, printlnを追加. System.outとSystem.errはPrintStream print(10); は文字列"10"を出力.C言語のprintfに相当 参考: System.inはInputStream ※ 歴史的経緯によりPrintStreamが残っている がPrintWriterを使うことを推奨 new PrintWriter(outputstream, true); new PrintWriter( new OutputStreamWriter(outputstream,”EUC-JP”), true); 出力したい 文字コードを 指定 15 printlnなどで、 Bufferをflushする ことを指定 参考:Unicode 日本語など,世界の主要な文字を含む 広く利用されるUTF-8では1文字を可変長 (1~4バイト)で表現 大抵は2バイトで収まる 0∼127の文字コードはASCIIと同じ. UTF-8, UTF-16などの複数の符号化方式が存在 ただし表現するバイト数は違う点に注意 unicode では __バイト,ASCIIでは __バイト Javaのchar型はUnicode. つまり,Javaの文字列はバイトストリームで単 純に扱えない 16 6 参考:データ・オブジェクトの直列化 直列化(serialize) オブジェクトをバイトストリームに変換する 簡略化した捉え方: int型のフィールドを2つ持つ Object Aは,int型 を表現するデータを2つ並べれば表現できる. つまり,(クラス定義と)このbyte streamを転送 すれば復元可能 DataInputStream, DataOutputStream intやdoubleなどの入出力に使う 環境の差異(バイトオーダー)を無視できる ObjectInputStream, ObjectOutputStream オブジェクトの入出力(serialize)に使う 17 プログラミング第三 第1部 オブジェクト指向・Java復習 Java API GUI (java.awt, javax.swing) 7 GUI プログラムの特徴 Event Driven(イベント駆動型) mainから順番に処理がされるのではない 「あるイベントが起こったらこの処理」 ウィンドウ設計 (部品の配置) 出力に文字列以外も使える 画像 入力にキーボード以外も使える ポインティングデバイス 19 イベント駆動型のプログラミング イベントハンドラが実行される仕組み イベントが発生 ボタンが押された、マウスでクリックされた イベントを待ち行列に格納 登録したイベントリスナが対応処理 D-2) 待ち行列に 格納 L-1) 監視したいイベントを指定して 登録する D-1) イベント の発生 D-3) 登録されている 各リスナーに順番に通知 L-2) 通知が来たら,イベント用の 処理(イベントハンドラ)を実行 する (それまではなにも 実行していない) 20 8 GUI: ウィンドウ設計 共通化された部品(コンポーネント)を 配置することで複雑なUIを構築する 部品 21 Swing Java2 SDKに含まれるGUIライブラリ パッケージ名は,javax.swing 通常,次をimportしてSwingを使う. javax.swing.*, java.awt.*, java.awt.event.* 実装手順 部品のオブジェクトを生成 部品の配置 イベント処理の設定 22 9 Swing GUIの構成要素 トップレベルコンテナ(ウィンドウなど) JFrame, JDialog, Japplet JFrameはメニューバー付きのウィンドウも作れる高 機能版 JDialogはloginウィンドウや、警告ウィンドウ用の単 純版 中間コンテナ JPanel, JScrollPane, JTabbedPane, JLayeredPane, … コンポーネントを乗せるお盆。中間コンテナを 使わずにトップレベルコンテナにコンポーネン トを直接乗せることもできる。 コンポーネント JButton, JLabel, JTextField, JTextArea, … 様々な機能を持ったGUIの部品 23 Swing GUIによる構成例 JFrameを使用した例: タイトル JFrame Menu Bar JButton Content Pane JFrame Content Pane Menu Bar その他 JButtonなど 左図のコンテナ階層構造 ※コンテナ階層のトップは 必ずトップレベルコンテナにする. 24 10 部品の配置 JFrameのコンテナを得る. 例:Container container = frame.getContentPane(); 部品のレイアウト(並べ方)を指定. 例:container.setLayout (new BorderLayout()); BorderLayout は東西南北と中央に配置するレイアウ トマネージャ.他にも BoxLayout, CardLayout, GridBagLayout, GroupLayout, SpringLayoutなどがある 部品を配置 例:container.add (textarea, BorderLayout.CENTER); 例:container.add (button, BorderLayout.NORTH); 25 Jframeを利用した例 import javax.swing.*; class Test1 { public static void main (String[] args) { final JFrame frame = new JFrame ("Window1"); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setSize (300, 200); frame.add(new JButton(“push”)); SwingUtilities.invokeLater(new Runnable(){ public void run(){ frame.setVisible (true); }}); } } 26 11 イベント処理の詳細 「イベント」を受け取って処理する ActionListener(インターフェース)を定義する GUIコンポーネントにActionListenerを登録する ( addListener() を使ってlistenersに追加する) キー入力やマウス操作の内容は「イベント」として, GUIコンポーネントに渡され, 各 ActionListener#actionPerformed()を呼び出すことで 処理が起動される JButtonの 実体 ボタン押下 のイベント 登録 ActionListenerの 実体 メソッド呼び出し actionPerformed() 27 例:JButtonにイベントハンドラを追加 import java.awt.event.*; import javax.swing.*; public class Notifier implements ActionListener{ public Notifier(){ } public void actionPerformed(ActionEvent e){ System.out.println("pushed!"); } public static void main(String[] args){ final JFrame jframe = new JFrame("EventTest"); JButton jbutton = new JButton("push me"); jbutton.addActionListener(new Notifier()); jframe.add(jbutton); jframe.pack(); SwingUtilities.invokeLater(new Runnable(){ public void run(){ jframe.setVisible (true); }}); } } %javac Notifier.java %java Notifier pushed! pushed! 部品の大きさで ウィンドウの大きさを決定 ウィンドウ表示 28 12 マウスを使ったサンプル import java.awt.*; import java.awt.event.*; import javax.swing.*; public class Drawing2 extends JPanel implements MouseMotionListener, ActionListener { volatile Point pnt = new Point(0,0); volatile private Boolean clear=true; public Drawing2(){ addMouseMotionListener(this); } public void paintComponent(Graphics g){ if(clear){ g.clearRect(0,0,600,400); clear=false; }else{ g.fillRect(pnt.x,pnt.y,2,2); } } public void mouseDragged(MouseEvent e){ pnt = e.getPoint(); repaint(); } public void mouseMoved(MouseEvent e){ } public void actionPerformed(ActionEvent e){ clear = true; repaint(); } public static void main(String[] args){ final JFrame jframe = new JFrame("mouseEventTest"); Drawing2 drawing = new Drawing2(); drawing.setPreferredSize(new Dimension(600,400)); JButton jbutton = new JButton("clear"); jbutton.addActionListener(drawing); Container container = jframe.getContentPane(); container.setLayout(new BorderLayout()); jframe.add(drawing,BorderLayout.NORTH); jframe.add(jbutton,BorderLayout.SOUTH); jframe.pack(); jframe.setResizable(false); jframe.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); SwingUtilities.invokeLater(new Runnable(){ public void run(){ jframe.setVisible (true); }}); } } 29 マウスを使ったサンプル import java.awt.*; import java.awt.event.*; import javax.swing.*; public class Drawing2 extends JPanel implements MouseMotionListener, ActionListener { JPanelのSubclassとして作成 MouseMotionListener 追加属性 volatile Point pnt = new Point(0,0); volatile private Boolean clear=true; public Drawing2(){ addMouseMotionListener(this); } public void paintComponent(Graphics g){ if(clear){ g.clearRect(0,0,600,400); clear=false; }else{ g.fillRect(pnt.x,pnt.y,2,2); } } public void mouseDragged(MouseEvent e){ pnt = e.getPoint(); repaint(); } JPanel の実装を継承して利用 マウスの移動イベントをListen pnt という座標(Point) clear というフラグ 描画処理:clearが真なら領域を クリアそうでないならば 点を 描画 fillRect(int x, int y, int width, int height) (x,y)を左端上端として,width*heightの 矩形を塗りつぶす. マウスがドラッグされた時の イベントハンドラ イベントに含まれている座標を pnt 属性として,再描画する 30 13 マウスを使ったサンプル public void mouseMoved(MouseEvent e){ } public void actionPerformed(ActionEvent e){ clear = true; repaint(); } マウスカーソルが移動したときのハン ドラ:何もしない ActionEventが来た場合のハンドラ public static void main(String[] args){ final JFrame jframe = new JFrame("mouseEventTest"); Drawing2 drawing = new Drawing2(); drawing.setPreferredSize(new Dimension(600,400)); JButton jbutton = new JButton("clear"); jbutton.addActionListener(drawing); Container container = jframe.getContentPane(); container.setLayout(new BorderLayout()); jframe.add(drawing,BorderLayout.NORTH); jframe.add(jbutton,BorderLayout.SOUTH); jframe.pack(); jframe.setResizable(false); jframe.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); SwingUtilities.invokeLater(new Runnable(){ public void run(){ jframe.setVisible (true); }}); } clearフラグをセットしてrepaint Panel(Drawing2)のサイズを指定 作成したボタンのリス何登録 フレームサイズの変更不可 Closeボタンを押された時の振る舞い 規定されている EXIT_ON_CLOSEを設定 } 31 イベント処理の流れ MouseMotionListener MouseDragged() MouseMoved() MouseMotionListener インタフェース の実装として呼出 ActionListener MouseEvent actionPerformed() MouseEvent ActionListener インタフェース の実装として呼出 ActionEvent Drawing2 Point pnt boolean clear paintComponent(g){ pnt clearを使っての 実際の描画実装 } mouseDragged(){ pntに値をセット repaint(); } mouseMoved(){ } actionPerformed(){ clearに値をセット repaint(); } JPanel repaint() paintComponent(g); 実際はJPanelのさらに上 位の基底クラスまで遡って 処理され、処理の待ち行 列に処理要求が格納され ...と、長くなる. ここでは、repaint()を呼び 出すと、巡り巡って paintComponent()が呼び 出されるという理解でよい 32 14 Swingの詳しい使い方 Java API のドキュメントを参照 http://docs.oracle.com/javase/jp/7/technotes/ guides/swing/index.html そのほかのDemoを参照 追加ファイルのダウンロードが必要 Java SDK には含まれない ので注意 demo/jfc/SwingSet2/に サンプルソースあり 33 15
© Copyright 2024 ExpyDoc