目标

  • 模拟实现一个基于文本界面的《客户信息管理软件》
  • 进一步掌握编程技巧和调试技巧,熟悉面向对象编程
  • 主要涉及以下知识点:
    • 类结构的使用:属性、方法及构造器
    • 对象的创建与使用
    • 类的封装性
    • 声明和使用数组
    • 数组的插入、删除和替换
    • 关键字的使用:this

需求说明

  • 模拟实现基于文本界面的《拼电商客户管理系统》。
  • 该软件能够实现对客户对象的插入、修改和删除(用数组实现),并能够打印客户明细表。
  • 项目采用分级菜单方式。主菜单如下:
1
2
3
4
5
6
7
8
9
-----------------客户信息管理软件-----------------

1 添 加 客 户
2 修 改 客 户
3 删 除 客 户
4 客 户 列 表
5 退 出

请选择(1-5):

添加客户

1
2
3
4
5
6
7
8
9
请选择(1-5):1

---------------------添加客户---------------------
姓名:佟刚
性别:男
年龄:35
电话:010-56253825
邮箱:tongtong@atguigu.com
---------------------添加完成---------------------

修改客户

1
2
3
4
5
6
7
8
9
10
请选择(1-5):2

---------------------修改客户---------------------
请选择待修改客户编号(-1退出):1
姓名(佟刚):<直接回车表示不修改>
性别(男):
年龄(35):
电话(010-56253825):
邮箱(tongtong@atguigu.com):tongg@atguigu.com
---------------------修改完成---------------------

删除客户

1
2
3
4
5
6
请选择(1-5):3

---------------------删除客户---------------------
请选择待删除客户编号(-1退出):1
确认是否删除(Y/N):y
---------------------删除完成---------------------

客户列表

1
2
3
4
5
6
7
8
请选择(1-5):4

---------------------------客户列表---------------------------
编号 姓名 性别 年龄 电话 邮箱
1 佟刚 男 45 010-56253825 tong@abc.com
2 封捷 女 36 010-56253825 fengjie@ibm.com
3 雷丰阳 男 32 010-56253825 leify@163.com
-------------------------客户列表完成-------------------------

软件设计结构

该软件由以下三个模块组成:

  • CustomerView为主模块,负责菜单的显示和处理用户操作
  • CustomerList为Customer对象的管理模块,内部用数组管理一组Customer对象,并提供相应的添加、修改、删除和遍历方法,供CustomerView调用
  • Customer为实体对象,用来封装客户信息

CMUtility 类

项目中提供了CMUtility.java类,可用来方便地实现键盘访问

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
package com.base.learn;

import java.util.*;

public class CMUtility {
private static Scanner scanner = new Scanner(System.in);
/**
用于界面菜单的选择。该方法读取键盘,如果用户键入’1’-’5’中的任意字符,则方法返回。返回值为用户键入字符。
*/
public static char readMenuSelection() {
char c;
for (; ; ) {
String str = readKeyBoard(1, false);
c = str.charAt(0);
if (c != '1' && c != '2' &&
c != '3' && c != '4' && c != '5') {
System.out.print("选择错误,请重新输入:");
} else break;
}
return c;
}
/**
从键盘读取一个字符,并将其作为方法的返回值。
*/
public static char readChar() {
String str = readKeyBoard(1, false);
return str.charAt(0);
}
/**
从键盘读取一个字符,并将其作为方法的返回值。
如果用户不输入字符而直接回车,方法将以defaultValue 作为返回值。
*/
public static char readChar(char defaultValue) {
String str = readKeyBoard(1, true);
return (str.length() == 0) ? defaultValue : str.charAt(0);
}
/**
从键盘读取一个长度不超过2位的整数,并将其作为方法的返回值。
*/
public static int readInt() {
int n;
for (; ; ) {
String str = readKeyBoard(2, false);
try {
n = Integer.parseInt(str);
break;
} catch (NumberFormatException e) {
System.out.print("数字输入错误,请重新输入:");
}
}
return n;
}
/**
从键盘读取一个长度不超过2位的整数,并将其作为方法的返回值。
如果用户不输入字符而直接回车,方法将以defaultValue 作为返回值。
*/
public static int readInt(int defaultValue) {
int n;
for (; ; ) {
String str = readKeyBoard(2, true);
if (str.equals("")) {
return defaultValue;
}

try {
n = Integer.parseInt(str);
break;
} catch (NumberFormatException e) {
System.out.print("数字输入错误,请重新输入:");
}
}
return n;
}
/**
从键盘读取一个长度不超过limit的字符串,并将其作为方法的返回值。
*/
public static String readString(int limit) {
return readKeyBoard(limit, false);
}
/**
从键盘读取一个长度不超过limit的字符串,并将其作为方法的返回值。
如果用户不输入字符而直接回车,方法将以defaultValue 作为返回值。
*/
public static String readString(int limit, String defaultValue) {
String str = readKeyBoard(limit, true);
return str.equals("")? defaultValue : str;
}
/**
用于确认选择的输入。该方法从键盘读取‘Y’或’N’,并将其作为方法的返回值。
*/
public static char readConfirmSelection() {
char c;
for (; ; ) {
String str = readKeyBoard(1, false).toUpperCase();
c = str.charAt(0);
if (c == 'Y' || c == 'N') {
break;
} else {
System.out.print("选择错误,请重新输入:");
}
}
return c;
}

private static String readKeyBoard(int limit, boolean blankReturn) {
String line = "";

while (scanner.hasNextLine()) {
line = scanner.nextLine();
if (line.length() == 0) {
if (blankReturn) return line;
else continue;
}

if (line.length() < 1 || line.length() > limit) {
System.out.print("输入长度(不大于" + limit + ")错误,请重新输入:");
continue;
}
break;
}

return line;
}
}

Customer 类

  • Customer为实体类,用来封装客户信息
  • 该类封装客户的以下信息:
    • String name :客户姓名
    • char gender :性别
    • int age :年龄
    • String phone:电话号码
    • String email :电子邮箱
  • 提供各属性的 get/set 方法
  • 提供所需的构造器(可自行确定)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
package com.base.learn;

/**
* 客户信息类:Customer
*
*/
public class Customer {
private String name; // 名字
private char gender; // 性别
private int age; // 年龄
private String phone; // 手机号
private String email; // 电子邮箱

public Customer() {
}

public Customer(String name, char gender, int age, String phone, String email) {
this.name = name;
this.gender = gender;
this.age = age;
this.phone = phone;
this.email = email;
}

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}

public char getGender() {
return gender;
}

public void setGender(char gender) {
this.gender = gender;
}

public int getAge() {
return age;
}

public void setAge(int age) {
this.age = age;
}

public String getPhone() {
return phone;
}

public void setPhone(String phone) {
this.phone = phone;
}

public String getEmail() {
return email;
}

public void setEmail(String email) {
this.email = email;
}
}

CustomerList 类

  • CustomerList为Customer对象的管理模块,内部使用数组管理一组Customer对象
  • 本类封装以下信息:
    • Customer[] customers:用来保存客户对象的数组
    • int total = 0 :记录已保存客户对象的数量
  • 该类至少提供以下构造器和方法:
    • public CustomerList(int totalCustomer)
    • public boolean addCustomer(Customer customer)
    • public boolean replaceCustomer(int index, Customer cust)
    • public boolean deleteCustomer(int index)
    • public Customer[] getAllCustomers()
    • public Customer getCustomer(int index)
    • public int getTotal()
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
package com.base.learn;

/**
* CustomerList 为 Customer 对象的管理模块
*
*/
public class CustomerList {
private Customer[] customers; // 用来保存客户对象的数组
private int total; // 记录已经保存客户对象的数量

/**
* 用来初始化 customers 数组的构造器
*
* @param totalCustomer 指定数组的长度
*/
public CustomerList(int totalCustomer) {
customers = new Customer[totalCustomer];
}

/**
* 将指定的客户添加到数组中
*
* @param customer 用户
* @return true:添加成功、false:添加失败
*/
public boolean addCustomer(Customer customer) {
if (total >= customers.length) {
return false;
}
// 将指定客户添加到数组中,并 total +1
customers[total++] = customer;
return true;
}

/**
* 修改指定位置的客户信息
*
* @param index 索引位置
* @param cust 用户
* @return true:修改成功、false:修改失败
*/
public boolean replaceCustomer(int index, Customer cust) {
// index 索引取值必须在[0, total)
if (index >= total || index < 0) {
return false;
}
customers[index] = cust;
return true;
}

/**
* 删除指定索引位置的客户信息
*
* @param index 索引位置
* @return true:修改成功、false:修改失败
*/
public boolean deleteCustomer(int index) {
// index 索引取值必须在[0, total)
if (index >= total || index < 0) {
return false;
}
for (int i = index; i < total - 1; i++) {
customers[i] = customers[i + 1];
}
// 最后的元素需要置为null
customers[--total] = null;
return true;
}

/**
* 获取所有的客户信息
*
* @return custs[]
*/
public Customer[] getAllCustomers() {
Customer[] custs = new Customer[total];
for (int i = 0; i < total; i++) {
custs[i] = customers[i];
}
return custs;
}

/**
* 获取指定索引位置上的客户
*
* @param index 索引位置
* @return 如果找到了元素,则返回;如果没有找到则返回 null
*/
public Customer getCustomer(int index) {
if (index >= total || index < 0) {
return null;
}
return customers[index];
}

/**
* 获取存储的客户数量
*
* @return total
*/
public int getTotal() {
return total;
}
}

CustomerView 类

  • CustomerView 为主模块,负责菜单的显示和处理用户操作
  • 本类封装以下信息:
    • CustomerList customerList = new CustomerList(10);
    • 创建最大包含10个客户对象的CustomerList 对象,供以下各成员方法使用。
  • 该类至少提供以下方法:
    • public void enterMainMenu()
    • private void addNewCustomer()
    • private void modifyCustomer()
    • private void deleteCustomer()
    • private void listAllCustomers()
    • public static void main(String[] args)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
package com.base.learn;

/**
* CustomerView 为主模块,负责菜单的显示和处理用户操作
*
*/
public class CustomerView {
private CustomerList customerList = new CustomerList(10);

public CustomerView() {
Customer customer = new Customer("张三", '男', 23, "177xxxx0143", "lanxxxxxg@126.com");
customerList.addCustomer(customer);
}

/**
* 显示《客户信息管理软件》界面的方法
*/
public void enterMainMenu() {
boolean isFlag = true;
do {
System.out.println("\n-----------------客户信息管理软件-----------------\n");
System.out.println(" 1 添 加 客 户");
System.out.println(" 2 修 改 客 户");
System.out.println(" 3 删 除 客 户");
System.out.println(" 4 客 户 列 表");
System.out.println(" 5 退 出\n");
System.out.print(" 请选择(1-5):");

char key = CMUtility.readMenuSelection();
System.out.println();
switch (key) {
case '1':
addNewCustomer();
break;
case '2':
modifyCustomer();
break;
case '3':
deleteCustomer();
break;
case '4':
listAllCustomers();
break;
case '5':
System.out.println("确认是否退出(Y/N):");
char yn = CMUtility.readConfirmSelection();
if (yn == 'Y') {
isFlag = false;
}
break;
}
} while (isFlag);

}

/**
* 添加客户操作
*/
public void addNewCustomer() {
System.out.println("---------------------------添加客户---------------------------");
System.out.println("姓名:");
String name = CMUtility.readString(10);
System.out.println("性别:");
char gender = CMUtility.readChar();
System.out.println("年龄:");
int age = CMUtility.readInt();
System.out.println("电话:");
String phone = CMUtility.readString(11);
System.out.println("邮箱:");
String email = CMUtility.readString(30);

// 将上述数据封装到对象中
Customer customer = new Customer(name, gender, age, phone, email);
boolean isSuccess = customerList.addCustomer(customer);
if (isSuccess) {
System.out.println("---------------------------添加成功---------------------------");
} else {
System.out.println("---------------------------添加失败---------------------------");
}
}

/**
* 修改客户操作,选择重新 new 对象的方式进行修改客户操作
*/
public void modifyCustomer() {
System.out.println("---------------------------修改客户---------------------------");
Customer cust;
int number;
for (; ; ) {
System.out.print("请选择待修改客户的编号(-1退出):");
number = CMUtility.readInt();
if (number == -1) {
return;
}
cust = customerList.getCustomer(number - 1);
if (cust == null) {
System.out.println("无法找到指定的客户!");
} else {
break;
}
}
// 修改客户相关信息
System.out.print("姓名(" + cust.getName() + "):");
String name = CMUtility.readString(10, cust.getName());
System.out.print("性别(" + cust.getGender() + "):");
char gender = CMUtility.readChar(cust.getGender());
System.out.print("年龄(" + cust.getAge() + "):");
int age = CMUtility.readInt(cust.getAge());
System.out.print("电话(" + cust.getPhone() + "):");
String phone = CMUtility.readString(13, cust.getPhone());
System.out.print("邮箱(" + cust.getEmail() + "):");
String email = CMUtility.readString(30, cust.getEmail());

Customer newCust = new Customer(name, gender, age, phone, email);
boolean isRepalaced = customerList.replaceCustomer(number - 1, newCust);
if (isRepalaced) System.out.println("---------------------------修改成功---------------------------");
else System.out.println("---------------------------修改失败---------------------------");
}

/**
* 删除客户操作
*/
public void deleteCustomer() {
System.out.println("---------------------------删除客户---------------------------");
Customer cust;
int number;
for (; ; ) {
System.out.print("请选择待删除改客户的编号(-1退出):");
number = CMUtility.readInt();
if (number == -1) {
return;
}
cust = customerList.getCustomer(number - 1);
if (cust == null) {
System.out.println("无法找到指定的客户!");
} else {
break;
}
}
System.out.println("确认是否删除(Y/N)");
char isDelete = CMUtility.readConfirmSelection();
if (isDelete == 'Y') {
boolean deleteSuccess = customerList.deleteCustomer(number - 1);
if(deleteSuccess) System.out.println("---------------------------删除成功---------------------------");
else System.out.println("---------------------------删除失败---------------------------");
}
}

/**
* 显示客户列表操作
*/
public void listAllCustomers() {
System.out.println("---------------------------客户列表---------------------------");
// 获取用户数量
int total = customerList.getTotal();
// 获取用户列表
Customer[] custs = customerList.getAllCustomers();

if (total == 0) {
System.out.println("没有客户记录...");
} else {
System.out.println("编号\t\t姓名\t\t性别\t\t年龄\t\t电话\t\t\t邮箱");
for (int i = 0; i < custs.length; i++) {
Customer cust = custs[i];
System.out.println((i + 1) + "\t\t" + cust.getName() + "\t\t" + cust.getGender()
+ "\t\t" + cust.getAge() + "\t\t" + cust.getPhone() + "\t\t" + cust.getEmail());
}
}
System.out.println("-------------------------客户列表完成--------------------------");
}

public static void main(String[] args) {
CustomerView view = new CustomerView();
view.enterMainMenu();
}
}