Java编程思想第4版 第13章 课后习题

练习1:分析reusing/SprinklerSystem.java的SprinklerSystem.toString()方法,看看明确地使用StringBuilder是否确实能够避免产生过多的StringBuilder对象。 

package test13.Ex01;

import javax.xml.transform.Source;

class WaterSource {
    private String s;

    WaterSource() {
        System.out.println("WaterSource()");
        s = "Constructed";
    }

    public String toString() {
        return s;
    }
}

public class SprinklerSystem {
    private String s1,s2,s3, s4;
    private WaterSource waterSource = new WaterSource();
    private int i;
    private float f;

    public String toString() {
        return
                "s1=" + s1 + " " +
                        "s2=" + s2 + " " +
                        "s3=" + s3 + " " +
                        "s4=" + s4 + " \n" +
                        "i=" + i + " " +
                        "f=" + f + " " +
                        "waterSource=" + waterSource + " ";    
    }
    public static void main(String[] args) {
        SprinklerSystem sprinklerSystem = new SprinklerSystem();
        System.out.println(sprinklerSystem);

    }
}

结果显示:

WaterSource()
s1=null s2=null s3=null s4=null 
i=0 f=0.0 waterSource=Constructed 

Process finished with exit code 0

练习2:(1)修复InfiniteRecursion.java。

package test13.Ex02;

import java.util.ArrayList;
import java.util.List;

public class InfiniteRecursion {
    public String toString() {
        return "InfiniteRecursion address: " + super.toString() + "\n";
    }

    public static void main(String[] args) {
        List<InfiniteRecursion> v = new ArrayList<>();
        for (int i = 0; i < 10; i++) {
            v.add(new InfiniteRecursion());
        }
        System.out.println(v);
    }
}

结果显示:

[InfiniteRecursion address: test13.Ex02.InfiniteRecursion@677327b6
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@14ae5a5
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@7f31245a
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@6d6f6e28
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@135fbaa4
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@45ee12a7
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@330bedb4
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@2503dbd3
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@4b67cf4d
, InfiniteRecursion address: test13.Ex02.InfiniteRecursion@7ea987ac
]

Process finished with exit code 0

练习3:(1)修改Turtle.java,使之将结果输出到System.err中。
 

package test13.Ex03;

import java.io.PrintStream;
import java.util.Formatter;

public class Turtle01 {
    private String name;
    private Formatter f;

    public Turtle01(String name, Formatter f) {
        this.name = name;
        this.f = f;
    }

    public void move(int x, int y) {
        f.format("%s The Turtle is at (%d,%d)\n", name, x, y);
    }

    public static void main(String[] args) {
        PrintStream outAlias = System.err;
        Turtle01 Tom = new Turtle01("Tom", new Formatter(System.err));
        Turtle01 Tony = new Turtle01("Tony", new Formatter(System.err));
        Tom.move(0, 0);
        Tony.move(4, 8);
        Tom.move(3, 4);
        Tony.move(2, 5);
        Tom.move(3, 3);
        Tony.move(3, 3);
    }
}

结果显示:

Tom The Turtle is at (0,0)
Tony The Turtle is at (4,8)
Tom The Turtle is at (3,4)
Tony The Turtle is at (2,5)
Tom The Turtle is at (3,3)
Tony The Turtle is at (3,3)

Process finished with exit code 0

练习4:(3)修改Receipt.java,令所有的宽度都由一个常量来控制。目的是使宽度的改变更容易,只需修改一处的值即可。

package test13.Ex04;

import java.util.Formatter;

public class Receipt01 {
    private double total = 0;
    private Formatter f = new Formatter(System.err);
    private static final int W1 = 15;
    private static final int W2 = 5;
    private static final int W3 = 10;
    private String s1 = "%-" + W1 + "s%" + W2 + "s%" + W3 + "s\n";
    private String s2 = "%-" + W1 + ".15s%" + W2 + "d%" + W3 + ".2f\n";
    private String s3 = "%-" + W1 + "s%" + W2 + "s%" + W3 + ".2f\n";

    public void printTitle() {
        f.format(s1, "Item", "Qty", "Price");
        f.format(s1, "----", "---", "-----");
    }

    public void print(String name,int qty,double price) {
        f.format(s2, name, qty, price);
        total += price;
    }

    public void printTotal() {
        f.format(s3, "Tax", "", total * 0.06);
        f.format(s1, "", "", "-----");
        f.format(s3, "Total", "", total * 1.06);
    }

    public static void main(String[] args) {
        Receipt01 receipt01 = new Receipt01();   
        receipt01.printTitle();
        receipt01.print("Jack's Magic Beans", 4, 4.25);
        receipt01.print("Princess peas", 3, 5.1);
        receipt01.print("Three Beans Porridge", 1, 14.29);
        receipt01.printTotal();
    }
}

结果显示:

Item             Qty     Price
----             ---     -----
Jack's Magic Be    4      4.25
Princess peas      3      5.10
Three Beans Por    1     14.29
Tax                       1.42
                         -----
Total                    25.06

Process finished with exit code 0

练习5:(5)针对前边表格中的各种基本转化类型,请利用所有可能的格式修饰符,写出一个尽可能复杂的格式化表达式。

package test13.Ex05;

import java.math.BigInteger;
import java.util.Formatter;

public class Ex05 {
    public static void main(String[] args) {
        Formatter f = new Formatter(System.err);
        char u = 'a';
        System.out.println("char u = \'a\'");
        f.format("%-2s%-2S%-2c%-2C%-5b%-5B%-3h%-3H\n", u, u, u, u, u, u, u, u);
        
        int v = 121;
        System.out.println("int v = 121");
        f.format("%-4s%-4S%-4d%-4c%-4C%-5b%-5B%-4x%-4X%-4h%-4H\n", v, v, v, v, v, v, v, v, v, v, v);
        
        BigInteger w = new BigInteger("50000000000000");
        System.out.println("BigInteger w = 50000000000000");
        f.format("%-15s%-15S%-15b%-15B%-15x%-15X%-15h%-15H\n", w, w, w, w, w, w, w, w);
        
        double x = 179.543;
        System.out.println("double = 179.543");
        f.format("%-8s%-8S%-5b%-5B%-15f%-15e%-15E%-12h%-12H\n", x, x, x, x, x, x, x, x, x);
        
        Boolean b = false;
        System.out.println("Boolean z = false");
        f.format("%-7s%-7S%-7b%-7B%-7h%-7H\n", b, b, b, b, b, b);
        
    }
}

结果显示:

char u = 'a'
int v = 121
BigInteger w = 50000000000000
double = 179.543
Boolean z = false
a A a A true TRUE 61 61 
121 121 121 y   Y   true TRUE 79  79  79  79  
50000000000000 50000000000000 true           TRUE           2d79883d2000   2D79883D2000   8842a1a7       8842A1A7       
179.543 179.543 true TRUE 179.543000     1.795430e+02   1.795430E+02   1ef462c     1EF462C     
false  FALSE  false  FALSE  4d5    4D5    

Process finished with exit code 0

练习6:(2)创建一个包含int、long、float与double元素的类。应用String.format()方法为这个类编写toString0方法,并证明它能正确工作。
 

package test13.Ex06;

public class Ex06 {
    int i = 0;
    long l = 0;
    float f = 0.0f;
    double d = 0.0;

    Ex06(int i, long l, float f, double d) {
        this.i = i;
        this.l = l;
        this.f = f;
        this.d = d;
    }

    public String toString() {
        return String.format("i=%d\nl=%d\nf=%.16g\nd=%.16g\n", i, l, f, d);
    }

    public static void main(String[] args) {
        Ex06 x = new Ex06(2, 451, 1.2f, 2.7182818289);
        Ex06 ex = new Ex06(-2147483648, -9223372036854775808L, 1.1754943508222875E-38f, 2.2250738585072014E-308);
        Ex06 exMax = new Ex06(2147483647, 9223372036854775807L, 3.4028234663852886E38f, 1.7976931348623157E308);
        System.out.println(x);
        System.out.println(ex);
        System.out.println(exMax);
    }
    
}

结果显示:

i=2
l=451
f=1.200000047683716
d=2.718281828900000

i=-2147483648
l=-9223372036854775808
f=1.175494350822288e-38
d=2.225073858507201e-308

i=2147483647
l=9223372036854775807
f=3.402823466385289e+38
d=1.797693134862316e+308


Process finished with exit code 0

练习7:(5)请参考java.util.regex.Pattern的文档,编写一个正则表达式,检查一个句子是否以大写字母开头,以句号结尾。

package test13.Ex07;


public class Ex07 {
    public static void main(String[] args) {
        String sen = "^[A-Z].*[.]$";
        String s1 = "Once upon a time.";
        String s2 = "abcd.";
        String s3 = "Abcd?";
        String s4 = "An easy way out.";
        String s5 = "Zorro.";
        String s6 = "X.";
        System.out.println(s1.matches(sen));
        System.out.println(s2.matches(sen));
        System.out.println(s3.matches(sen));
        System.out.println(s4.matches(sen));
        System.out.println(s5.matches(sen));
        System.out.println(s6.matches(sen));
        
    }
}

结果显示:

true
false
false
true
true
true

Process finished with exit code 0

练习8:(2)将字符串Splitting.knights在the和you处分割。

package test13.Ex08;

import java.util.Arrays;

public class Ex08 {
    public static String Knight = "Then, When you have found the shrubbery, you must " +
            "cut down the mightiest tree in the forest..." +
            "with... a herring!";

    public static void split(String regex) {
        System.out.println(Arrays.toString(Knight.split(regex)));
    }

    public static void main(String[] args) {
        split("the|you");
    }
}

结果显示:

[Then, When ,  have found ,  shrubbery, ,  must cut down ,  mightiest tree in ,  forest...with... a herring!]

Process finished with exit code 0

练习9:(4)参考java.util.regex.Pattern的文档,用下划线替换Splitting.knights中的所有元音字母。
 

package test13.Ex09;

public class Ex09 {
    public static String Knight = "Then, When you have found the shrubbery, you must " +
            "cut down the mightiest tree in the forest..." +
            "with... a herring!";
    public static void main(String[] args) {
        System.out.println(Knight.replaceAll("[aeiouAEIOU]","_"));
    }
}

结果显示:

Th_n, Wh_n y__ h_v_ f__nd th_ shr_bb_ry, y__ m_st c_t d_wn th_ m_ght__st tr__ _n th_ f_r_st...w_th... _ h_rr_ng!

Process finished with exit code 0

练习10:(2)对字符串Java now has regular expressions验证下列正则表达式是否能够发现一个匹配:

^Java
\Breg.*
n.w\s+h(a|i)s
s?
s*
s+
s{4}
s{1}.
s{0,3}
package test13.Ex10;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class Ex10 {
    public static void main(String[] args) {
        if (args.length < 2) {
            System.out.println("Usage:\njava TestRegularExpression " +
                    "characterSequence regularExpression+");
            System.exit(0);
            
        }
        System.out.println("Input: \"" + args[0] + "\"");
        for (String arg : args) {
            System.out.println("Regular expression: \"" + arg + "\"");
            Pattern p = Pattern.compile(arg);
            Matcher m = p.matcher(args[0]);
            if (!m.find()) {
                System.out.println("No match found for" + "\"" + arg + "\"");
            }
            m.reset();
            while (m.find()) {
                System.out.println("Match \"" + m.group() + "\" at position" +
                        m.start() + ((m.end() - m.start() < 2) ? "" : ("-" + (m.end() - 1))));
                
            }
        }
    }
}

结果显示:

Usage:
java TestRegularExpression characterSequence regularExpression+

Process finished with exit code 0

练习11:(2)试用正则表达式

(?i)((^[aeiou])|(\s+[aeiou]))\w+?[aeiou]\

匹配字符串Arline ate eight apples and one orange while Anita hadn't any。
"Arline ate eight apples and one orange while Anita hadn' t any"

package test13.Ex11;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class Ex11 {
    public static void main(String[] args) {
        Pattern p = Pattern.compile("(?i)((^[aeiou])|(\\s+[aeiou]))\\w+[aeiou]\\b");
        Matcher m = p.matcher("Arline ate eight apples and one orange while Anita hadn't any");
        while (m.find()) {
            System.out.println("Match \"" + m.group() + "\" at " + m.start());
        }
    }
}

结果显示:

Match "Arline" at 0
Match " ate" at 6
Match " one" at 27
Match " orange" at 31
Match " Anita" at 44

Process finished with exit code 0

练习12:(5)修改Goups.java类,找出所有不以大写字母开头的词,不重复地计算其个数。
 

package test13.Ex12;

import java.util.Set;
import java.util.TreeSet;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class Ex12 {
    static public final String POEM =
            "Twas brillig, and the slithy toves\n" +
                    "Did gyre and gimble in the wabe.\n" +
                    "All mimsy were the borogoves,\n" +
                    "And the mome raths outgrabe.\n\n" +
                    "Beware the Jabberwock, my son,\n" +
                    "The jaws that bite, the claws that catch,\n" +
                    "Beware the Jubjub bird, and shun\n" +
                    "The frumious Bandersnatch.";

    public static void main(String[] args) {
        Matcher m = Pattern.compile("(^[A-Z]|\\s+[a-z])\\w+").matcher(POEM);
        Set<String> words = new TreeSet<>();
        while (m.find()) {
            words.add(m.group());
        }
        System.out.println("Number of unique non-cap words = " + words.size());
        System.out.println(words);
    }
}

结果显示:

Number of unique non-cap words = 26
[ and,  bird,  bite,  borogoves,  brillig,  catch,  claws,  frumious,  gimble,  gyre,  in,  jaws,  mimsy,  mome,  my,  outgrabe,  raths,  shun,  slithy,  son,  that,  the,  toves,  wabe,  were, Twas]

Process finished with exit code 0

练习13:(2)修改StartEnd.java,让它使用Groups.POEM为输人,必要时修改正则表达式,使find()、lookingAt()和matches()都有机会匹配成功。
 

package test13.Ex13;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class Ex13 {
    public static String input =
            "Twas brillig, and the slithy toves\n" +
                    "Did gyre and gimble in the wabe.\n" +
                    "All mimsy were the borogoves,\n" +
                    "And the mome raths outgrabe.\n\n" +
                    "Beware the Jabberwock, my son,\n" +
                    "The jaws that bite, the claws that catch,\n" +
                    "Beware the Jubjub bird, and shun\n" +
                    "The frumious Bandersnatch.";

    private static class Display {
        private boolean regexPrinted = false;
        private String regex;

        Display(String regex) {
            this.regex = regex;
        }

        void display(String message) {
            if (!regexPrinted) {
                System.out.println(regex);
                regexPrinted = true;
            }
            System.out.println(message);
        }
    }

    static void examine(String s, String regex) {
        Display d = new Display(regex);
        Pattern p = Pattern.compile(regex);
        Matcher m = p.matcher(s);
        while (m.find()) {
            d.display("find() '" + m.group() + "' start = " + m.start() + " end =" + m.end());
        }
        if (m.lookingAt()) {
            d.display("lookingAt() start = " + m.start() + " end = " + m.end());
        }
        if (m.matches()) {
            d.display("matches() start = " + m.start() + " end = " + m.end());
        }
    }

    public static void main(String[] args) {
        for (String in : input.split("\n")) {
            System.out.println("input : " + in);
            for (String regex : new String[]{"\\w*are\\w*", "A\\w*", "T*\\w+", "Did.*"}) {
                examine(in, regex);
            }
            System.out.println();
        }
    }
}

结果显示:

input : Twas brillig, and the slithy toves
T*\w+
find() 'Twas' start = 0 end =4
find() 'brillig' start = 5 end =12
find() 'and' start = 14 end =17
find() 'the' start = 18 end =21
find() 'slithy' start = 22 end =28
find() 'toves' start = 29 end =34
lookingAt() start = 0 end = 4

input : Did gyre and gimble in the wabe.
T*\w+
find() 'Did' start = 0 end =3
find() 'gyre' start = 4 end =8
find() 'and' start = 9 end =12
find() 'gimble' start = 13 end =19
find() 'in' start = 20 end =22
find() 'the' start = 23 end =26
find() 'wabe' start = 27 end =31
lookingAt() start = 0 end = 3
Did.*
find() 'Did gyre and gimble in the wabe.' start = 0 end =32
lookingAt() start = 0 end = 32
matches() start = 0 end = 32

input : All mimsy were the borogoves,
A\w*
find() 'All' start = 0 end =3
lookingAt() start = 0 end = 3
T*\w+
find() 'All' start = 0 end =3
find() 'mimsy' start = 4 end =9
find() 'were' start = 10 end =14
find() 'the' start = 15 end =18
find() 'borogoves' start = 19 end =28
lookingAt() start = 0 end = 3

input : And the mome raths outgrabe.
A\w*
find() 'And' start = 0 end =3
lookingAt() start = 0 end = 3
T*\w+
find() 'And' start = 0 end =3
find() 'the' start = 4 end =7
find() 'mome' start = 8 end =12
find() 'raths' start = 13 end =18
find() 'outgrabe' start = 19 end =27
lookingAt() start = 0 end = 3

input : 

input : Beware the Jabberwock, my son,
\w*are\w*
find() 'Beware' start = 0 end =6
lookingAt() start = 0 end = 6
T*\w+
find() 'Beware' start = 0 end =6
find() 'the' start = 7 end =10
find() 'Jabberwock' start = 11 end =21
find() 'my' start = 23 end =25
find() 'son' start = 26 end =29
lookingAt() start = 0 end = 6

input : The jaws that bite, the claws that catch,
T*\w+
find() 'The' start = 0 end =3
find() 'jaws' start = 4 end =8
find() 'that' start = 9 end =13
find() 'bite' start = 14 end =18
find() 'the' start = 20 end =23
find() 'claws' start = 24 end =29
find() 'that' start = 30 end =34
find() 'catch' start = 35 end =40
lookingAt() start = 0 end = 3

input : Beware the Jubjub bird, and shun
\w*are\w*
find() 'Beware' start = 0 end =6
lookingAt() start = 0 end = 6
T*\w+
find() 'Beware' start = 0 end =6
find() 'the' start = 7 end =10
find() 'Jubjub' start = 11 end =17
find() 'bird' start = 18 end =22
find() 'and' start = 24 end =27
find() 'shun' start = 28 end =32
lookingAt() start = 0 end = 6

input : The frumious Bandersnatch.
T*\w+
find() 'The' start = 0 end =3
find() 'frumious' start = 4 end =12
find() 'Bandersnatch' start = 13 end =25
lookingAt() start = 0 end = 3


Process finished with exit code 0

练习14:(1)用String.split()重写SplitDemo。
 

package test13.Ex14;

import java.util.Arrays;

public class Ex14 {
    public static void main(String[] args) {
        String input = "This!!unusual use!!of exclamation!!points";
        System.out.println(Arrays.toString(input.split("!!")));
        System.out.println(Arrays.toString(input.split("!!", 3)));
    }
}

结果显示:

[This, unusual use, of exclamation, points]
[This, unusual use, of exclamation!!points]

Process finished with exit code 0

练习15:(5)修改JGrep.java类,令其能够接受模式标志参数(例如PatternINSENSITIVE,Pattern.MULTILINE)。
练习16:(5)修改JGrep.java类,令其能够接受一个目录或文件为参数(如果传入的是目录,就搜索目录中的所有文件)。提示:可以用下面的方法获得所有文件的名字列表:File[ ] files = new File("." ).listFiles();
练习17:(8)编写一个程序,读取一个Java源代码文件(可以通过控制台参数提供文件名),打印出所有注释。
练习18:(8)编写一个程序,读取一个Java源代码文件(可以通过控制台参数提供文件名),打印出代码中所有的普通字符串。
练习19:(8)在前两个练习的基础上,编写一个程序,输出Java源代码中用到的所有类的名字。
练习20:(2)编写一个包含int、long、float、double和String属性的类。为它编写一个构造器,接收一个String参数。然后扫描该字符串,为各个属性赋值。再添加一个toString(方法,用来演示你的类是否工作正确。

package test13.Ex20;

import java.util.Scanner;

public class Ex20 {
    int i;
    long l;
    float f;
    double d;
    String s ;

    Ex20(String s) {
        Scanner sc = new Scanner(s);
        i = sc.nextInt();
        l = sc.nextLong();
        f = sc.nextFloat();
        d = sc.nextDouble();
        this.s = sc.next();
        
    }

    public String toString() {
        return i + " " + l + " " + d + " " + s;
    }

    public static void main(String[] args) {
        Ex20 ex20 = new Ex20("17 45555555 2.5 3.333333 hello");
        System.out.println(ex20);
    }
}

结果显示:

17 45555555 3.333333 hello

Process finished with exit code 0


 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值