redisson hincrby 遇到的编码问题
一 问题
老项目的redis 要切换到redis集群,所以客户端从leettuce的RedisAsyncCommands切换到到redisson.
一个常见的hash增长:
public long hincrby(String key,String field,Long amount){
//新旧代码开关
if( 老的Redis){
老代码
}else{
新代码
}
}
redisClient.hincrby(key,field,amount).get()
查看下官网的对应操作手册:
https://www.bookstack.cn/read/redisson-wiki-zh/11.-Redis%E5%91%BD%E4%BB%A4%E5%92%8CRedisson%E5%AF%B9%E8%B1%A1%E5%8C%B9%E9%85%8D%E5%88%97%E8%A1%A8.md
HDEL | RMap.fastRemove(), RMap.fastRemoveAsync(), RMapReactive.fastRemove(); |
HEXISTS | RMap.containsKey(), RMap.containsKeyAsync(), RMapReactive.containsKey(); |
HGET | RMap.get(), RMap.getAsync(), RMapReactive.get(); |
HSTRLEN | RMap.valueSize(), RMap.valueSizeAsync(), RMapReactive.valueSize(); |
HGETALL | RMap.readAllEntrySet(), RMap.readAllEntrySetAsync(), RMapReactive.readAllEntrySet(); |
HINCRBY | RMap.addAndGet(), RMap.addAndGetAsync(), RMapReactive.addAndGet(); |
HINCRBYFLOAT | RMap.addAndGet(), RMap.addAndGetAsync(), RMapReactive.addAndGet(); |
HKEYS | RMap.readAllKeySet(), RMap.readAllKeySetAsync(), RMapReactive.readAllKeySet(); |
HLEN | RMap.size(), RMap.sizeAsync(), RMapReactive.size(); |
HMGET | RMap.getAll(), RMap.getAllAsync(), RMapReactive.getAll(); |
HMSET | RMap.putAll(), RMap.putAllAsync(), RMapReactive.putAll(); |
HSET | RMap.put(), RMap.putAsync(), RMapReactive.put(); |
HSETNX | RMap.fastPutIfAbsent(), RMap.fastPutIfAbsentAsync, RMapReactive.fastPutIfAbsent(); |
那就是Rmap.addandGet().
RMap<String, Long> map = redissonCilent.getMap(key);result = map.addAndGet(field,amount);
如果只是api级别的简单替换,没啥问题。
但是桌子涉及业务场景的时候,新老redis替换,数据要保证平滑。就是原来假设某个field 有值是9了,再调用就该返回10.
这时候切成新的redis集群,没同步就是从0开始,返回1了,这显然有问题。
因此考虑到平滑的问题,先给对应的值同步老数据。
map.put(field, oldnum );
这时候,打开开关切换到新的redisson集群,测试就报错了。
二 分析
错误很长,放到最后。看半天还是Google终于找到问题:看下RedissonMap 的底层实现
@Overridepublic V addAndGet(K key, Number value) {return get(addAndGetAsync(key, value));}@Overridepublic RFuture<V> addAndGetAsync(final K key, Number value) {checkKey(key);checkValue(value);final RFuture<V> future = addAndGetOperationAsync(key, value);if (hasNoWriter()) {return future;}MapWriterTask<V> listener = new MapWriterTask<V>() {@Overridepublic void execute() {options.getWriter().write(key, future.getNow());}};return mapWriterFuture(future, listener);}//核心protected RFuture<V> addAndGetOperationAsync(K key, Number value) {ByteBuf keyState = encodeMapKey(key);RFuture<V> future = commandExecutor.writeAsync(getName(key), StringCodec.INSTANCE,new RedisCommand<Object>("HINCRBYFLOAT", new NumberConvertor(value.getClass())),getName(key), keyState, new BigDecimal(value.toString()).toPlainString());return future;}
核心代码 就是 addAndGetOperationAsync
这里参数很多。调用了CommandAsyncExecutor 的
<T, R> RFuture<R> writeAsync(String key, Codec codec, RedisCommand<T> command, Object ... params);
这样看就清晰了,这里调用的RedisCommand命令是HINCRBYFLOAT,对应的编码是 StringCodec.INSTANCE。
引用下相关背景知识:
HINCRBYFLOAT key field increment
为哈希表 key 中的域 field 加上浮点数增量 increment 。
如果哈希表中没有域 field ,那么 HINCRBYFLOAT 会先将域 field 的值设为 0 ,然后再执行加法操作。
如果键 key 不存在,那么 HINCRBYFLOAT 会先创建一个哈希表,再创建域 field ,最后再执行加法操作。
当以下任意一个条件发生时,返回一个错误:
- 域 field 的值不是字符串类型(因为 redis 中的数字和浮点数都以字符串的形式保存,所以它们都属于字符串类型)
- 域 field 当前的值或给定的增量 increment 不能解释(parse)为双精度浮点数(double precision floating point number)
HINCRBYFLOAT 命令的详细功能和 INCRBYFLOAT 命令类似,请查看 INCRBYFLOAT 命令获取更多相关信息。
可用版本:
>= 2.6.0
时间复杂度:
O(1)
返回值:
执行加法操作之后 field 域的值。
我的入参是:Long 类型,我使用了默认编码:JsonJacksonCodec 。所以才报这个错误。
改为指定的编码,StringCodec 就可以了。
贴一下:redisson的编码集
Redisson的对象编码类是用于将对象进行序列化和反序列化,以实现对该对象在Redis里的读取和存储。Redisson提供了以下几种的对象编码应用,以供大家选择:
编码类名称 | 说明 |
---|---|
org.redisson.codec.JsonJacksonCodec
|
Jackson JSON 编码 默认编码 |
org.redisson.codec.AvroJacksonCodec
|
Avro 一个二进制的JSON编码 |
org.redisson.codec.SmileJacksonCodec
|
Smile 另一个二进制的JSON编码 |
org.redisson.codec.CborJacksonCodec
|
CBOR 又一个二进制的JSON编码 |
org.redisson.codec.MsgPackJacksonCodec
|
MsgPack 再来一个二进制的JSON编码 |
org.redisson.codec.IonJacksonCodec
|
Amazon Ion 亚马逊的Ion编码,格式与JSON类似 |
org.redisson.codec.KryoCodec
|
Kryo 二进制对象序列化编码 |
org.redisson.codec.SerializationCodec
|
JDK序列化编码 |
org.redisson.codec.FstCodec
|
FST 10倍于JDK序列化性能而且100%兼容的编码 |
org.redisson.codec.LZ4Codec
|
LZ4 压缩型序列化对象编码 |
org.redisson.codec.SnappyCodec
|
Snappy 另一个压缩型序列化对象编码 |
org.redisson.client.codec.JsonJacksonMapCodec
|
基于Jackson的映射类使用的编码。可用于避免序列化类的信息,以及用于解决使用byte[] 遇到的问题。
|
org.redisson.client.codec.StringCodec
|
纯字符串编码(无转换) |
org.redisson.client.codec.LongCodec
|
纯整长型数字编码(无转换) |
org.redisson.client.codec.ByteArrayCodec
|
字节数组编码 |
org.redisson.codec.CompositeCodec
|
用来组合多种不同编码在一起 |
最后贴一下错误日志:
hgetFromNewRedis error,key=ee
org.redisson.client.RedisException: Unexpected exception while processing commandat org.redisson.command.CommandAsyncService.convertException(CommandAsyncService.java:324) ~[redisson-3.5.6.jar:na]at org.redisson.command.CommandAsyncService.get(CommandAsyncService.java:167) ~[redisson-3.5.6.jar:na]at org.redisson.RedissonObject.get(RedissonObject.java:75) ~[redisson-3.5.6.jar:na]at org.redisson.RedissonMap.get(RedissonMap.java:251) ~[redisson-3.5.6.jar:na]at com.benmu.matador.workflow.RedisCommandProxy.hget(RedisCommandProxy.java:220) ~[matador-workflow-1.0.21.jar:na]at com.benmu.matador.integration.web.controller.DoorController.hget(DoorController.java:150) [DoorController.class:na]at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_71]at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_71]at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_71]at java.lang.reflect.Method.invoke(Method.java:497) ~[na:1.8.0_71]at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:221) [spring-web-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:136) [spring-web-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:110) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:817) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:731) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:85) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:959) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:893) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:968) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:859) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at javax.servlet.http.HttpServlet.service(HttpServlet.java:621) [servlet-api.jar:na]at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:844) [spring-webmvc-4.2.5.RELEASE.jar:4.2.5.RELEASE]at javax.servlet.http.HttpServlet.service(HttpServlet.java:728) [servlet-api.jar:na]at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305) [catalina.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) [catalina.jar:7.0.47]at com.benmu.matador.integration.web.security.PrivilegeFilter.doFilter(PrivilegeFilter.java:52) [PrivilegeFilter.class:na]at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243) [catalina.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) [catalina.jar:7.0.47]at com.benmu.matador.integration.web.security.LoginFilter.doFilter(LoginFilter.java:47) [LoginFilter.class:na]at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243) [catalina.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) [catalina.jar:7.0.47]at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51) [tomcat7-websocket.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243) [catalina.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) [catalina.jar:7.0.47]at com.benmu.ServletWatcher.doFilter(ServletWatcher.java:137) [common-core-1.3.3.jar:na]at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243) [catalina.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) [catalina.jar:7.0.47]at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:121) [spring-web-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) [spring-web-4.2.5.RELEASE.jar:4.2.5.RELEASE]at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243) [catalina.jar:7.0.47]at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) [catalina.jar:7.0.47]at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222) [catalina.jar:7.0.47]at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123) [catalina.jar:7.0.47]at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502) [catalina.jar:7.0.47]at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171) [catalina.jar:7.0.47]at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100) [catalina.jar:7.0.47]at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:953) [catalina.jar:7.0.47]at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118) [catalina.jar:7.0.47]at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408) [catalina.jar:7.0.47]at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1041) [tomcat-coyote.jar:7.0.47]at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:603) [tomcat-coyote.jar:7.0.47]at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:312) [tomcat-coyote.jar:7.0.47]at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) [na:1.8.0_71]at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) [na:1.8.0_71]at java.lang.Thread.run(Thread.java:745) [na:1.8.0_71]
Caused by: java.lang.IndexOutOfBoundsException: readerIndex(0) + length(4) exceeds writerIndex(1): SlicedAbstractByteBuf(ridx: 0, widx: 1, cap: 1/1, unwrapped: PooledUnsafeDirectByteBuf(ridx: 7, widx: 7, cap: 512))at io.netty.buffer.AbstractByteBuf.checkReadableBytes0(AbstractByteBuf.java:1411) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.buffer.AbstractByteBuf.readInt(AbstractByteBuf.java:764) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at org.redisson.codec.SnappyCodec$3.decode(SnappyCodec.java:74) ~[redisson-3.5.6.jar:na]at org.redisson.client.handler.CommandDecoder.decode(CommandDecoder.java:257) ~[redisson-3.5.6.jar:na]at org.redisson.client.handler.CommandDecoder.decode(CommandDecoder.java:101) ~[redisson-3.5.6.jar:na]at io.netty.handler.codec.ReplayingDecoder.callDecode(ReplayingDecoder.java:367) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:248) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:348) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:334) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:326) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.ChannelInboundHandlerAdapter.channelRead(ChannelInboundHandlerAdapter.java:86) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:348) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:334) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:326) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.ChannelInboundHandlerAdapter.channelRead(ChannelInboundHandlerAdapter.java:86) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:348) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:334) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:326) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.ChannelInboundHandlerAdapter.channelRead(ChannelInboundHandlerAdapter.java:86) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:348) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:334) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:326) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1320) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:348) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:334) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:905) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:123) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:563) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:504) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:418) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:390) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.util.concurrent.SingleThreadEventExecutor$5.run(SingleThreadEventExecutor.java:742) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]at io.netty.util.concurrent.DefaultThreadFactory$DefaultRunnableDecorator.run(DefaultThreadFactory.java:145) ~[netty-all-4.1.1.Final.jar:4.1.1.Final]... 1 common frames omitted
我一开始围绕错误日志搜关键词,netty的数组越界问题,搜出来都是不太想干的问题。还是去看下底层代码更有收获。
希望对你有所帮助。
参考:
http://doc.redisfans.com/hash/hincrbyfloat.html
https://github.com/redisson/redisson/issues/870
redisson hincrby 遇到的编码问题相关推荐
- 聊聊分布式锁——Redis和Redisson的方式
聊聊分布式锁--Redis和Redisson的方式 一.什么是分布式锁 分布式~~锁,要这么念,首先得是『分布式』,然后才是『锁』 分布式:这里的分布式指的是分布式系统,涉及到好多技术和理论,包括CA ...
- redis watchdog_Redis分布式事务框架Redisson源码解析(一)
代码片段一. public static void main(String[] args) throws Exception { Config config = new Config(); confi ...
- Redis客户端框架Redisson
介绍 Redisson是架设在Redis基础上的一个Java驻内存数据网格(In-Memory Data Grid). Redisson在基于NIO的Netty框架上,充分的利用了Redis键值数据库 ...
- redisson使用全解——redisson官方文档+注释(中篇)
文章目录 八.分布式锁和同步器(重要!) 8.1. 可重入锁(Reentrant Lock) 8.2. 公平锁(Fair Lock) 8.3. 联锁(MultiLock) 8.4. 红锁(RedLoc ...
- redisson版本_Redis客户端redisson实战
redis客户端redisson实战 1.前言 Redisson是一个基于java编程框架netty进行扩展了的redis,想了解Redisson源码首先你必须熟悉netty网络编程框架.html R ...
- Redisson 是如何实现分布式锁的?
点击上方蓝色"程序猿DD",选择"设为星标" 回复"资源"获取独家整理的学习资料! 作者 | bravoban 来源 | tech.lede ...
- Redis进阶- Redisson分布式锁实现原理及源码解析
文章目录 Pre 用法 Redisson分布式锁实现原理 Redisson分布式锁源码分析 redisson.getLock(lockKey) 的逻辑 redissonLock.lock()的逻辑 r ...
- Redisson 分布式锁实现分析(一)
Why 分布式锁 java.util.concurrent.locks 中包含了 JDK 提供的在多线程情况下对共享资源的访问控制的一系列工具,它们可以帮助我们解决进程内多线程并发时的数据一致性问题. ...
- redisson MultiLock原理及分布式锁的应用
一.前言 基于 Redis 的 Redisson 分布式联锁 RedissonMultiLock 对象可以将多个 RLock 对象关联为一个联锁,每个 RLock 对象实例可以来自于不同的 Redis ...
最新文章
- MPB:军科院杨瑞馥、毕玉晶等-​​培养组学方法优化(视频)
- dockerfile各种命令解析
- 【Python基础】14_Python中的TODO注释
- 从零开始html css,HTML/CSS从零开始-常用属性(三)
- Android应用清单文件:AndroidManifest.xml
- fseek/ftell/rewind/fgetpos/fsetpos函数使用-linux
- 区分错误类型_汽车轮胎更换标准轮胎类型选择方式-详解
- 很现实、很暴力的面试法则 —— 来自招聘官的自述
- 毫米波雷达和车联网在未来无人驾驶中的应用和比较
- cmd无法运行python_通过Java-%1在cmd中运行python文件不是有效的Win32应用程序 - java...
- java上传ftp_java实现FTP文件上传与文件下载
- ipsec over gre与gre over ipsec
- 快速解决cmd命令行乱码问题
- 怎样用计算机将二进制转换成十进制,二进制如何转换为十进制?
- php汉字存储容量大小,存储400个24*24点阵汉字字形所需的存储容量是多少
- PHP高效率写法(详解原因)
- C语言之基本算法15—前三位和后三位都是完全平方数的六位完全平方数
- 未来,能源枯竭可以逆转吗?
- Java生成无限制带参小程序码
- WPS 手动去除广告
热门文章
- realmeq2pro和红米note10pro的区别
- Excel的数据类型转换方法
- 合图分割工具SpriteSplit
- matlab在动态分析中的应用图,功率键合图和Matlab/Simulink在液压系统动态仿真分析中的应用...
- 东方梦符祭服务器无响应,东方梦符祭常见问题汇总 东方梦符祭常见问题解决方案...
- 史上最全Java工程师面试题汇总,全会月薪至少3W
- 嘉为蓝鲸CMP:跳出云管看云管(IT运维/混合云/一体化/云管理)
- 实现微信绑定用户功能
- 毕业设计 深度学习 机器视觉 车位识别车道线检测 - python opencv
- docker 运行java程序_Docker:在容器中运行Java应用程序