好久都没交总结了,今天把之前的思路和错误整理了一下:
在服务器和客户端两侧,不可以同时先初始化获取输入流,否则会造成堵塞,同时为这位作者大大打call:
(3条消息) 关于Java Socket和创建输入输出流的几点注意_明明班长的博客-CSDN博客
还有就是如果客户端和服务器想要用同一个类,可以在两边都复制相同的类,但是要注意,如果这个类在包下,一定要将包也复制一份不然你都不知道自己怎么错的QAQ; 比如在客户端是这样的:
也就是common包包下有一个这个类,但是服务端也要用到这个类,这时候可以把它复制过去:
重要的事说三遍,记得复制包包也要一样,包名要一样!!!
还有就是在写鼠标点击或者键盘的按压事件(当然,按钮就不要了,按钮有一个专门的方法Action)后要在这个ideal里面这样改,不然事件不匹配;
进去控制类对应的fxml文件,然后将 其打开,在有黄色的鼠标点击事件或者键盘按压事件右击show...什么的,也就是第一个,然后有一个change。。。的会弹出来一个弹框直接点击refactor就行了。(QAQ有点抽象)
如果fxml和view没有在一个包下,比如我是这样的,就要将路径都改成这样的:也就是加载fxml是这样写:
Parent root = FXMLLoader.load(LoginView.class.getClassLoader().getResource("fxml/login.fxml") );
如果想要在不是某个控制器类的组件下用该组件,有这样一个模板获得该控制器,先是在view界面这样写:
public class ChatRoomView {
public static Stage chatRoomStage;
private static ChatRoomController controller; // 添加一个控制器对象的引用
public static void start(Stage primaryStage) throws IOException {
chatRoomStage = primaryStage;
FXMLLoader loader = new FXMLLoader(ChatRoomView.class.getClassLoader().getResource("fxml/chatroom.fxml"));
Parent root = loader.load();
controller = loader.getController(); // 获取FXML文件关联的控制器对象
primaryStage.setTitle("小花花聊天室");
primaryStage.setScene(new Scene(root, 800, 600));
primaryStage.show();
}
public static ChatRoomController getController() {
return controller;
}
}
字符串比较一定要用equals,不然自己怎么错了都不知道。少用”==“少用,少用!!!但是不得不说,equals只能是等于,所以用不等于可以在前面加一个!记得添上括号;
还有就是静态变量不可以序列化,熟记熟记熟记,当然如果实在想要序列化可以取巧,比如在一个列里面想要将这个类静态化便于利用,但是又要传,这时候可以定一个临时变量和这个要传的变量同类型;将静态变量赋值给它,本人亲测,真的可以😁;
一般一个输入流对应一个输出流,如果涉及到socket的话,最好两个同时关闭,不要用完一个关闭一个,不然第二个用不了;比如用完输出流输出一次之后就关了,这时候再读取就用不了,因为这时候关闭输出流的时候将socket也给关了;但是正规关闭最后还是要关socket的;
如果在初始化写某个临时组件的点击事件没有用的话,可能是你的顺序放错了,理清思路。(比如有一些是要先在初始化方法里面现附上初始值才可以操作,这时候赋值操作就一定要在这个前面了),还有就是一般一个界面打开一次才动用一次初始化方法,但是如果这个初始化方法里面有点击事件导致界面大幅度变化的也会触发初始化方法;
至于为什么和User用户类有仇我也不想纠结了,换一个名字就不会数据错乱了,所以没去深究,值得说的是,在多个请求情况下,哪怕有些数据是有先后顺序的,还是要对两边的通讯设置接受条件,以防数据传错,所以说,数据的判断条件最好放在一个类里面,不然会很心累TAT~;
还有就是在Javafx里面,有一个UI界面的主线程,但是有一些界面UI更新比较慢(涉及到要去数据库什么的获取数据),会阻塞主线程,导致界面卡死,这时候可以通过Task类和Platform来辅助实现:比如我这个点击事件:
friendList.setOnMouseClicked(event -> {
Friend selectedFriend = friendList.getSelectionModel().getSelectedItem();
getMy = selectedFriend;
accountt.add(getMy.getAccount());
accountt.add(ManageClientToThread.u.getUserAccount());
// 创建一个后台任务来加载聊天记录数据
Task<ArrayList<Message>> getFriendsTask = new Task<ArrayList<Message>>() {
@Override
protected ArrayList<Message> call() throws Exception {
if (tempMessage != null) {
new MessageClientService().insertMessage(tempMessage);
}
imageA=ucs1.imageAvar(accountt);
return new MessageClientService().initMessagerecord(ManageClientToThread.u.getUserAccount(), selectedFriend.getAccount());
}
};
// 设置任务完成后的处理逻辑
getFriendsTask.setOnSucceeded(e -> {
ArrayList<Message> messages = getFriendsTask.getValue();
// 在主线程中更新UI
Platform.runLater(() -> {
// 清空聊天框中的内容
flowPane1.getChildren().clear();
// 将加载的聊天记录填充到聊天框中
for (Message msg : messages) {
System.out.println("加一个消息");
addBox(msg);
}
System.out.println("到底来了不?");
});
});
// 启动任务
Thread thread = new Thread(getFriendsTask);
thread.setDaemon(true); // 设置为守护线程(可选)
thread.start();
});
批量查询不是什么其他的,只能是execute或者executeQuery,Batch不可以用于查询,不可以!!!
关于类静态变量没有过构造器这件事,切记切记,要用初始化用静态构造块,真的要记住!!!
关于正则判断,我真的要说五遍,表示路径里面的一个单线杠要用四个‘\’(单引号里面的,不包括单引号);这里是chat的一点解释,主要是靠自己理解QAQ:
目前就是这些,把自己之前受过的委屈发出来真是太爽了!!!
然后再稍稍励志一下:如果这段时间你觉得很疲惫,觉得全是坎坷,请相信这是老天对你赐福的考验,熬过了这段时间,接下来全是好运。