1. Pengenalan
Dalam tutorial ini, kami akan menunjukkan cara menguraikan aliran watak menjadi token menggunakan kelas Java StreamTokenizer .
2. StreamTokenizer
The StreamTokenizer kelas membaca watak strim dengan watak. Masing-masing mempunyai sifar atau lebih daripada atribut berikut: ruang kosong, abjad, angka, petikan rentetan atau watak komen.
Sekarang, kita perlu memahami konfigurasi lalai. Kami mempunyai jenis watak berikut:
- Watak perkataan : berkisar seperti 'a' hingga 'z' dan 'A' hingga 'Z
- Aksara berangka : 0,1,…, 9
- Aksara ruang kosong : Nilai ASCII dari 0 hingga 32
- Watak komen : /
- Huruf petikan rentetan : 'dan'
Perhatikan bahawa hujung garis dianggap sebagai ruang kosong, bukan sebagai token yang berasingan, dan komen gaya C / C ++ tidak dikenali secara lalai.
Kelas ini mempunyai sekumpulan bidang penting:
- TT_EOF - Pemalar yang menunjukkan akhir aliran
- TT_EOL - Pemalar yang menunjukkan hujung garisan
- TT_NUMBER - Pemalar yang menunjukkan token nombor
- TT_WORD - Pemalar yang menunjukkan token perkataan
3. Konfigurasi Lalai
Di sini, kita akan membuat contoh untuk memahami mekanisme StreamTokenizer . Kami akan mulakan dengan membuat contoh kelas ini dan kemudian memanggil kaedah nextToken () sehingga mengembalikan nilai TT_EOF :
private static final int QUOTE_CHARACTER = '\''; private static final int DOUBLE_QUOTE_CHARACTER = '"'; public static List streamTokenizerWithDefaultConfiguration(Reader reader) throws IOException { StreamTokenizer streamTokenizer = new StreamTokenizer(reader); List tokens = new ArrayList(); int currentToken = streamTokenizer.nextToken(); while (currentToken != StreamTokenizer.TT_EOF) { if (streamTokenizer.ttype == StreamTokenizer.TT_NUMBER) { tokens.add(streamTokenizer.nval); } else if (streamTokenizer.ttype == StreamTokenizer.TT_WORD || streamTokenizer.ttype == QUOTE_CHARACTER || streamTokenizer.ttype == DOUBLE_QUOTE_CHARACTER) { tokens.add(streamTokenizer.sval); } else { tokens.add((char) currentToken); } currentToken = streamTokenizer.nextToken(); } return tokens; }
Fail ujian hanya mengandungi:
3 quick brown foxes jump over the "lazy" dog! #test1 //test2
Sekarang, jika kita mencetak kandungan array, kita akan melihat:
Number: 3.0 Word: quick Word: brown Word: foxes Word: jump Word: over Word: the Word: lazy Word: dog Ordinary char: ! Ordinary char: # Word: test1
Untuk lebih memahami contohnya, kita perlu menerangkan bidang StreamTokenizer.ttype , StreamTokenizer.nval dan StreamTokenizer.sval .
The ttype bidang mengandungi jenis cara yang hanya membaca. Ia mungkin TT_EOF , TT_EOL , TT_NUMBER , TT_WORD . Walau bagaimanapun, untuk token rentetan yang disebut, nilainya adalah nilai ASCII bagi watak petikan. Lebih-lebih lagi, jika token itu adalah watak biasa seperti '!' , tanpa atribut, maka ttype akan diisi dengan nilai ASCII watak itu.
Seterusnya, kami menggunakan medan sval untuk mendapatkan token, hanya jika itu adalah TT_WORD , iaitu token kata. Tetapi, jika kita berurusan dengan token rentetan yang dikutip - katakan "malas" - maka bidang ini mengandungi isi rentetan.
Terakhir, kami telah menggunakan medan nval untuk mendapatkan token, hanya jika itu adalah token nombor, menggunakan TT_NUMBER .
4. Konfigurasi Tersuai
Di sini, kita akan mengubah konfigurasi lalai dan membuat contoh lain.
Pertama, kita akan menetapkan beberapa watak kata tambahan menggunakan kaedah wordChars (int rendah, int hi) . Kemudian, kami akan menjadikan watak komen ('/') yang biasa dan mempromosikan '#' sebagai watak komen baru.
Akhirnya, kita akan menganggap hujung baris sebagai watak token dengan bantuan kaedah eolIsSignificant (boolean flag) .
Kita hanya perlu memanggil kaedah ini pada objek streamTokenizer :
public static List streamTokenizerWithCustomConfiguration(Reader reader) throws IOException { StreamTokenizer streamTokenizer = new StreamTokenizer(reader); List tokens = new ArrayList(); streamTokenizer.wordChars('!', '-'); streamTokenizer.ordinaryChar('/'); streamTokenizer.commentChar('#'); streamTokenizer.eolIsSignificant(true); // same as before return tokens; }
Dan di sini kita mempunyai output baru:
// same output as earlier Word: "lazy" Word: dog! Ordinary char: Ordinary char: Ordinary char: / Ordinary char: / Word: test2
Perhatikan bahawa tanda petik menjadi sebahagian daripada token, watak barisan baru bukan watak ruang kosong lagi, tetapi watak biasa, dan oleh itu token watak tunggal.
Juga, watak-watak yang mengikuti watak '#' kini dilangkau dan '/' adalah watak biasa.
Kita juga boleh mengubah watak petikan dengan kaedah quoteChar (int ch) atau bahkan watak ruang kosong dengan memanggil kaedah whitespaceChars (int rendah, int hi) . Oleh itu, penyesuaian lebih lanjut dapat dilakukan dengan memanggil kaedah StreamTokenizer dalam kombinasi yang berbeza .
5. Kesimpulan
Dalam tutorial ini, kita telah melihat cara menguraikan aliran watak menjadi token menggunakan kelas StreamTokenizer . Kami telah mengetahui tentang mekanisme lalai dan membuat contoh dengan konfigurasi lalai.
Akhirnya, kami telah mengubah parameter lalai dan kami menyedari betapa fleksibelnya kelas StreamTokenizer .
Seperti biasa, kodnya boleh didapati di GitHub.