1.“try-with-resource are not supported at language level “5” ”
百度后发现:maven是个项目管理工具,如果我们不告诉它我们的代码要使用什么样的jdk版本编译的话,它就会用maven-compiler-plugin默认的jdk版本来进行处理,这样就容易出现版本不匹配,以至于可能导致编译不通过的问题。
maven的默认编译使用的jdk版本很低(很明显是5),使用maven-compiler-plugin插件可以指定项目源码的jdk版本,编译后的jdk版本,以及编码。
参考资料:IDEA 报错:not supported at language level "5"_enhanced 'switch' blocks are not supported at lang-优快云博客
2.logger.info()报错原因(没有这个方法)
第一看lombok插件 第二看依赖
<dependencies>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.8</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.3</version> <!-- 使用最新版本 -->
</dependency>
</dependencies>
3.class<T> clazz;clazz.cast(object obj)
就是obj强制转换为clazz类型
4.java try() 括号里面的资源自动关闭
@Override
public byte[] serialize(Object obj) {
// 为什么在try里面写,try里的资源自动关闭
try (ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
Output output = new Output(byteArrayOutputStream)) {
Kryo kryo = KRYO_THREAD_LOCAL.get();
// Object->byte:将对象序列化为byte数组
kryo.writeObject(output, obj);
KRYO_THREAD_LOCAL.remove();
return output.toBytes();
} catch (Exception e) {
throw new SerializeException("序列化失败");
}
}
5.sed命令
在您提供的命令中,sed
是一个流编辑器,用于对文本文件进行查找、替换、删除、插入等操作。这个特定的命令使用 sed
来替换 /etc/yum.repos.d/docker-ce.repo
文件中的文本。下面是命令的详细解释:
sudo sed -i 's|https://mirrors.aliyun.com|http://mirrors.cloud.aliyuncs.com|g' /etc/yum.repos.d/docker-ce.repo
-
sed
: 调用 sed 程序。 -
-i
: 这个选项告诉sed
直接修改文件内容,而不是输出到标准输出(通常是屏幕)。这意味着原文件将被修改后的版本替换。 -
's|https://mirrors.aliyun.com|http://mirrors.cloud.aliyuncs.com|g'
: 这是sed
的替换命令,其结构为s|原字符串|新字符串|标志
。s
: 表示替换操作。|
: 这里用作分隔符。通常,sed
使用/
作为分隔符(如s/原字符串/新字符串/g
),但你可以使用任何字符作为分隔符,这在处理包含很多/
的字符串时特别有用。https://mirrors.aliyun.com
: 要被替换的原始字符串。http://mirrors.cloud.aliyuncs.com
: 替换后的新字符串。g
: 表示全局替换,即替换行中所有匹配的实例,而不仅仅是第一个。
-
/etc/yum.repos.d/docker-ce.repo
: 要被编辑的文件路径。
简而言之,这个命令的作用是将 /etc/yum.repos.d/docker-ce.repo
文件中所有的 https://mirrors.aliyun.com
替换为 http://mirrors.cloud.aliyuncs.com
。这种替换通常用于更改软件仓库的镜像地址,可能是因为原来的镜像地址不再可用或者为了使用更快的镜像服务。
6.crul测试网络请求是否能成功连接
curl -v https://registry-1.docker.io/v2/
7.docker常用命令
# 查看docker版本
docker version
# 列出本地所有镜像
docker images
# 查看当前运行的容器
docker ps
# 登陆到Docker Hub
docker login iregistry.baidu-int.com -u 用户名 -p 密码
# 拉取镜像到本地
docker pull iregistry.baidu-int.com/[项目名]/[镜像库名字]:[tag名字]
# 构建自己的镜像
docker build -t <镜像名> <Dockerfile路径>
# 以交互式的方式(选项-it)启动一个名为test(选项--name)的容器,使用镜像docker.paddlepaddlehub.com/paddle_manylinux_devel:cuda8.0_cudnn5
# 容器运行结束后自动清理其所产生的数据(选项--rm)
docker run -it --rm --name test iregistry.baidu-int.com/paddlecloud/paddlecloud-runenv-ubuntu16.04-online:paddlecloud-paddle-v2.1.2-gcc820-cuda10.1_cudnn7
8.docker pull zookeeper出错:registry-1.docker.io不可以访问报错
参考资料:安装 Docker:安装Docker并使用镜像仓库ACR_云服务器 ECS(ECS)-阿里云帮助中心
如果docker hub访问问题:使用阿里云指定的镜像:从阿里云登录 - 欢迎登录阿里云,安全稳定的云计算服务平台查找,每个用户都可能不一样!!!
报错:
2月 10 15:32:41 iZ0jlhho33h3sln0h2967vZ dockerd[5237]: time="2025-02-10T15:32:41.328334539+08:00" level=info msg="Attempting next endpoint for pull after error: Get \"https://registry-1.docker.io/v2/\": context deadline exceeded (Client.Timeout exceeded while awaiting headers)" spanID=fbf0af0536c81932 traceID=59019e97d370164967de39a3bfd2126f
2月 10 15:32:41 iZ0jlhho33h3sln0h2967vZ dockerd[5237]: time="2025-02-10T15:32:41.336370246+08:00" level=error msg="Handler for POST /v1.45/images/create returned error: Get \"https://registry-1.docker.io/v2/\": context deadline exceeded (Client.Timeout exceeded while awaiting headers)" spanID=fbf0af0536c81932 traceID=59019e97d370164967de39a3bfd2126f
9.已知端口号 看是否被占用+pid
被占用listening
netstat -lutnp | grep 2181
tcp6 0 0 :::2181 :::* LISTEN 18526/dockerd
10.关于日志在控制台输出希望info error warning有不同颜色
展示就下图的样式就够了:
在本文章2.问题的基础之上,新建resources目录:下面来一个logback.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="CONSOLE" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{YY:MM:dd-HH:mm:ss} [%24.24thread] %highlight(%-5level) %logger{36} - %msg%n</pattern>
</encoder>
</appender>
<root level="DEBUG">
<appender-ref ref="CONSOLE" />
</root>
<conversionRule conversionWord="highlight" converterClass="org.slf4j.helpers.MessageFormatter">
<cOpt>red</cOpt>
</conversionRule>
</configuration>
11.RpcServiceProperties
是哪个包的(手写rpc)
是 org.apache.dubbo.config
包中的一个类,用于配置 Dubbo 框架中 RPC 服务的相关属性。Dubbo 是一个高性能的 Java RPC 框架,广泛用于分布式服务架构中
12.为啥用泛型(手写rpc)
一代码复用,二减少显式转换
13.【经典错误】Exception in thread "Thread-2" Exception in thread "Thread-1" Exception in thread "Thread-0" java.lang.IllegalMonitorStateException
Exception in thread "Thread-2" Exception in thread "Thread-1" Exception in thread "Thread-0" java.lang.IllegalMonitorStateException at java.lang.Object.notifyAll(Native Method) at concurrent.PrintStuff$1AThread.run(PrintStuff.java:29) java.lang.IllegalMonitorStateException at java.lang.Object.wait(Native Method) at java.lang.Object.wait(Object.java:502) at concurrent.PrintStuff$1BThread.run(PrintStuff.java:40) java.lang.IllegalMonitorStateException at java.lang.Object.wait(Native Method) at java.lang.Object.wait(Object.java:502) at concurrent.PrintStuff$1CThread.run(PrintStuff.java:59)
第1次打印,Thread-0 a
在你的代码中,wait()
和 notifyAll()
的调用没有完全包裹在 synchronized
块中,导致线程没有持有锁的情况下调用了这些方法,从而抛出 IllegalMonitorStateException
。
关键修正点
-
synchronized
块包裹wait()
和notifyAll()
:-
确保
wait()
和notifyAll()
都在synchronized (lock)
块中调用。 -
这样线程在调用
wait()
或notifyAll()
时,会持有lock
对象的监视器锁。
-
-
while
循环检查条件:-
使用
while (ch != 'a')
而不是if
,防止虚假唤醒(spurious wakeup)。
-
-
volatile
关键字:-
ch
变量用volatile
修饰,确保多线程之间的可见性。
-
14.顺序打印abc常见的错误
第1次打印,Thread-0 a
第1次打印,Thread-1 b
第1次打印,Thread-2 c
Process finished with exit code 130
这个是因为我没有用notifyall 我用了notify 我有多个线程需要唤醒却用了notify 就会阻塞!!!!
分析一下这个过程:
- AThread 开始执行,打印 'a',然后改变
ch
为 'b',并调用lock.notifyAll()
。 - 此时,如果 BThread 或 CThread 中的一个或多个线程正在
lock.wait()
上等待,它们将被唤醒。 - 被唤醒的线程(假设是 BThread)会重新检查
while (ch != 'b')
条件。如果条件满足(即ch
确实是 'b'),它将继续执行,打印 'b',然后改变ch
为 'c',并再次调用lock.notifyAll()
。 - 同理,如果 CThread 被唤醒,并且
ch
是 'c',它将执行打印 'c',然后改变ch
为 'a',并调用lock.notifyAll()
。
在Java中,synchronized
关键字用于创建同步代码块或方法,它确保同一时刻只有一个线程可以执行该代码块或方法。当线程尝试进入synchronized
代码块或方法时,如果锁已经被其他线程持有,那么该线程将会被阻塞(不是立即进入wait
状态),直到锁被释放。
而wait()
和notifyAll()
是Object
类中的方法,它们用于在线程之间进行通信。当线程调用wait()
方法时,它必须持有某个对象的锁。调用wait()
后,线程会释放该对象的锁并进入等待状态(wait set),直到其他线程调用同一个对象的notify()
或notifyAll()
方法来唤醒它。
现在,关于您的问题:
- 唤醒所有想要争取同一把锁的线程:
notifyAll()
方法确实会唤醒等待同一个对象锁的所有线程。但是,这些线程被唤醒后并不会立即获得锁。它们需要重新竞争锁,就像任何其他尝试进入synchronized
代码块或方法的线程一样。
- 等待包括两个状态,一个是进入synchronized的时候一个是lock wait的时候:
- 这个描述有些混淆。当线程尝试进入
synchronized
代码块或方法时,如果锁被其他线程持有,它会被阻塞(blocked),而不是立即进入wait
状态。阻塞状态与等待状态(wait state)是不同的。 - 等待状态(wait state)是线程调用
wait()
方法后所处的状态。在这个状态下,线程已经释放了锁,并且不会参与锁的竞争,直到被notify()
或notifyAll()
唤醒。
- 这个描述有些混淆。当线程尝试进入
15.ConcurrentModificationException异常
使用foreach循环遍历:一般不建议在foreach循环中直接修改正在遍历的List元素,因为这可能会导致意外的结果或ConcurrentModificationException异常。