mysql udp服务器_netty学习:UDP服务器与Spring整合(2)

上一篇文章中,介绍了netty实现UDP服务器的栗子。

本文将会对UDP服务器与spring boot整合起来,并使用RedisTemplate的操作类访问Redis和使用Spring DATA JPA链接MySQL数据库,其中会使用多线程、异步等知识。

只公布了一个框架,需要的同学可以根据此来进行扩展,增加自己需要的功能模块。如Controller部分。

本人使用的编辑器是IntelliJ IDEA 2017.1.exe版本(链接:http://pan.baidu.com/s/1pLODHm7 密码:dlx7);建议使用STS或者是idea编辑器来进行spring的学习。

1)项目目录结构

整个项目的目录结构如下:

7a30ef99a1c73278302c11020d7bd976.png

2)jar包

其中pom.xml文件的内容如下:

只有netty-all和commons-lang3是手动加入的jar包,其余的都是创建spring boot项目时候选择组件后自动导入的。

1 <?xml version="1.0" encoding="UTF-8"?>

2

3 xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

4 4.0.0

5

6 com.example

7 udplearning

8 0.0.1-SNAPSHOT

9 jar

10

11 udplearning

12 Demo project for Spring Boot

13

14

15 org.springframework.boot

16 spring-boot-starter-parent

17 1.5.6.RELEASE

18

19

20

21

22 UTF-8

23 UTF-8

24 3.4

25 1.8

26

27

28

29

30

31

32

33 io.netty

34 netty-all

35 4.0.49.Final

36

37

38

39

40 org.apache.commons

41 commons-lang3

42 ${commons-lang3.version}

43

44

45

46

47

48 org.springframework.boot

49 spring-boot-starter-data-jpa

50

51

52 org.springframework.boot

53 spring-boot-starter-data-redis

54

55

56 org.springframework.boot

57 spring-boot-starter-jdbc

58

59

60 org.springframework.boot

61 spring-boot-starter-web

62

63

64 org.springframework.boot

65 spring-boot-starter-web-services

66

67

68

69 mysql

70 mysql-connector-java

71 runtime

72

73

74 org.springframework.boot

75 spring-boot-starter-test

76 test

77

78

79

80

81

82

83 org.springframework.boot

84 spring-boot-maven-plugin

85

86

87

88

89

90

3)配置文件application.properties

application.properties的内容:

1 spring.profiles.active=test2

3 spring.messages.encoding=utf-8

4

5 logging.config=classpath:logback.xml

“spring.profiles.active” 针对多种启动环境的spring boot配置方法,此时启动的是test运行环境,即默认是启动application-test.properties里面的配置信息;

“spring.messages.encoding=utf-8”是指编码方式utf-8;

“logging.config=classpath:logback.xml”是指日志文件位置。

application-test.properties的内容如下:

1 context.listener.classes=com.example.demo.init.StartupEvent2

3 #mysql4 spring.jpa.show-sql=true

5 spring.jpa.database=mysql6 #spring.jpa.hibernate.ddl-auto=update7 spring.datasource.url=jdbc:mysql://127.0.0.1/test

8 spring.datasource.username=root9 spring.datasource.password=123456

10 spring.datasource.driver-class-name=com.mysql.jdbc.Driver11 spring.datasource.jdbc-interceptors=ConnectionState;SlowQueryReport(threshold=0)12

13 spring.session.store-type=none14

15 # (RedisProperties)16 spring.redis.database=3

17 spring.redis.host=127.0.0.1

18 spring.redis.port=6379

19 spring.redis.password=123456

20 spring.redis.pool.max-active=8

21 spring.redis.pool.max-wait=-1

22 spring.redis.pool.max-idle=8

23 spring.redis.pool.min-idle=0

24 spring.redis.timeout=0

25

26

27 #UDP消息接收打端口28 sysfig.udpReceivePort = 7686

29

30 #线程池31 spring.task.pool.corePoolSize = 5

32 spring.task.pool.maxPoolSize = 100

33 spring.task.pool.keepAliveSeconds = 100

34 spring.task.pool.queueCapacity = 100

其中配置了context.listener.classes=com.example.demo.init.StartupEvent,将StartupEvent类作为Spring boot启动后执行文件。

其中还配置了一些mysql、redis和自定义的属性。可根据项目的实际情况修改。

4)日志文件logback.xml

logback.xml的内容如下:

1 <?xml version="1.0" encoding="UTF-8"?>

2

3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

4 xsi:schemaLocation="http://ch.qos.logback/xml/ns/logback

5 http://ch.qos.logback/xml/ns/logback/logback.xsd

6 http://ch.qos.logback/xml/ns/logback ">

7

8

9 ${APP_Name}

10

11

12

13 %d{yyyyMMddHHmmss}|%-5level| %logger{0}.%M | %msg | %thread %n

14

15

16

17

18

19 ${catalina.home}/logs/app.%d{yyyyMMdd}.log

20 30

21

22

23 %d{yyMMddHHmmss.SSS}|%-5level| %msg%n

24

25

26

27

28

29 ${catalina.home}/logs/run.%d{yyyyMMdd}.log

30 7

31

32

33 %d{yyMMddHHmmss.SSS}|%-5level| %msg%n

34

35

36

37

38

39

40

41

42

43

44

45

日志的级别是info级别  可以根据自己项目的实际情况进行设置。

5)StartupEvent.java

1 packagecom.example.demo.init;2

3 importorg.slf4j.Logger;4 importorg.slf4j.LoggerFactory;5 importorg.springframework.context.ApplicationContext;6 importorg.springframework.context.ApplicationListener;7 importorg.springframework.context.event.ContextRefreshedEvent;8

9 /**

10 *11 * Created by wj on 2017/8/28.12 */

13

14 public class StartupEvent implements ApplicationListener{15 private static final Logger log = LoggerFactory.getLogger(StartupEvent.class);16

17 private staticApplicationContext context;18

19 @Override20 public voidonApplicationEvent(ContextRefreshedEvent contextRefreshedEvent) {21

22 try{23

24 context =contextRefreshedEvent.getApplicationContext();25

26 SysConfig sysConfig = (SysConfig) context.getBean(SysConfig.class);27

28 //接收UDP消息并保存至redis中

29 UdpServer udpServer = (UdpServer)StartupEvent.getBean(UdpServer.class);30 udpServer.run(sysConfig.getUdpReceivePort());31

32

33 //这里可以开启多个线程去执行不同的任务34 //此处为工作的内容,不便公开!

35

36

37 } catch(Exception e) {38 log.error("Exception", e);39 }40 }41

42 public staticObject getBean(Class beanName) {43 return context != null ? context.getBean(beanName) : null;44 }45 }

6)UdpServer.java

1 packagecom.example.demo.init;2

3 importcom.example.demo.handle.UdpServerHandler;4 importio.netty.bootstrap.Bootstrap;5 importio.netty.channel.ChannelOption;6 importio.netty.channel.EventLoopGroup;7 importio.netty.channel.nio.NioEventLoopGroup;8 importio.netty.channel.socket.nio.NioDatagramChannel;9 importorg.slf4j.Logger;10 importorg.slf4j.LoggerFactory;11 importorg.springframework.scheduling.annotation.Async;12 importorg.springframework.stereotype.Component;13

14 /**

15 * server服务器16 * Created by wj on 2017/8/30.17 */

18 @Component19 public classUdpServer {20

21 private static final Logger log= LoggerFactory.getLogger(UdpServer.class);22

23 //private static final int PORT = Integer.parseInt(System.getProperty("port", "7686"));

24

25 @Async("myTaskAsyncPool")26 public void run(intudpReceivePort) {27

28 EventLoopGroup group = newNioEventLoopGroup();29 log.info("Server start! Udp Receive msg Port:" +udpReceivePort );30

31 try{32 Bootstrap b = newBootstrap();33 b.group(group)34 .channel(NioDatagramChannel.class)35 .option(ChannelOption.SO_BROADCAST, true)36 .handler(newUdpServerHandler());37

38 b.bind(udpReceivePort).sync().channel().closeFuture().await();39 } catch(InterruptedException e) {40 e.printStackTrace();41 } finally{42 group.shutdownGracefully();43 }44 }45

46 }

此处NioDatagramChannel.class采用的是非阻塞的模式接受UDP消息,若是接受的UDP消息少,可以采用阻塞式的方式接受UDP消息。

UdpServer.run()方法使用@Async将该方法定义成异步的,myTaskAsyncPool是自定义的线程池。

7)UdpServerHandler.java

1 packagecom.example.demo.handle;2

3 importcom.example.demo.init.StartupEvent;4 importcom.example.demo.mod.UdpRecord;5 importcom.example.demo.repository.mysql.UdpRepository;6 importcom.example.demo.repository.redis.RedisRepository;7 importio.netty.buffer.Unpooled;8 importio.netty.channel.ChannelHandlerContext;9 importio.netty.channel.SimpleChannelInboundHandler;10 importio.netty.channel.socket.DatagramPacket;11 importio.netty.util.CharsetUtil;12 importorg.apache.commons.lang3.StringUtils;13 importorg.slf4j.Logger;14 importorg.slf4j.LoggerFactory;15

16 importjava.sql.Timestamp;17 importjava.util.Date;18

19 /**

20 * 接受UDP消息,并保存至redis的list链表中21 * Created by wj on 2017/8/30.22 *23 */

24

25 public class UdpServerHandler extends SimpleChannelInboundHandler{26

27 private static final Logger log= LoggerFactory.getLogger(UdpServerHandler.class);28

29 //用来计算server接收到多少UDP消息

30 private static int count = 0;31

32 @Override33 public void channelRead0(ChannelHandlerContext ctx, DatagramPacket packet) throwsException {34

35 String receiveMsg =packet.content().toString(CharsetUtil.UTF_8);36

37 log.info("Received UDP Msg:" +receiveMsg);38

39 UdpRecord udpRecord = newUdpRecord();40

41 //判断接受到的UDP消息是否正确(未实现)

42 if(StringUtils.isNotEmpty(receiveMsg) ){43

44 //计算接收到的UDP消息的数量

45 count++;46

47 //获取UdpRepository对象,将接收UDP消息的日志保存至mysql中

48 udpRecord.setUdpMsg(receiveMsg);49 udpRecord.setTime(getTime());50 UdpRepository udpRepository = (UdpRepository) StartupEvent.getBean(UdpRepository.class);51 udpRepository.save(udpRecord);52

53 //获取RedirRepository对象

54 RedisRepository redisRepository = (RedisRepository) StartupEvent.getBean(RedisRepository.class);55 //将获取到的UDP消息保存至redis的list列表中

56 redisRepository.lpush("udp:msg", receiveMsg);57 redisRepository.setKey("UDPMsgNumber", String.valueOf(count));58

59

60 //在这里可以返回一个UDP消息给对方,告知已接收到UDP消息,但考虑到这是UDP消息,此处可以注释掉

61 ctx.write(newDatagramPacket(62 Unpooled.copiedBuffer("QOTM: " + "Got UDP Message!", CharsetUtil.UTF_8), packet.sender()));63

64 }else{65 log.error("Received Error UDP Messsage:" +receiveMsg);66 }67 }68

69 @Override70 public voidchannelReadComplete(ChannelHandlerContext ctx) {71 ctx.flush();72 }73

74 @Override75 public voidexceptionCaught(ChannelHandlerContext ctx, Throwable cause) {76 cause.printStackTrace();77 //We don't close the channel because we can keep serving requests.

78 }79

80 publicTimestamp getTime(){81 Date date = newDate();82 Timestamp time = newTimestamp(date.getTime());83 returntime;84 }85

86 }

此处若不借用ApplicationContext.getBean,是无法获取到RedisRepository对象的。

注:这里是无法使用注解@Autowired来获取到redisTemplate对象的。

8)repository

RedisRepository.java

1 packagecom.example.demo.repository.redis;2

3 importorg.slf4j.Logger;4 importorg.slf4j.LoggerFactory;5 importorg.springframework.beans.factory.annotation.Autowired;6 importorg.springframework.data.redis.core.RedisTemplate;7 importorg.springframework.stereotype.Service;8

9 /**

10 * 链接redis11 * 实现list lpush和rpop12 * Created by wj on 2017/8/30.13 */

14

15

16 @Service17 public classRedisRepository {18 private static final Logger log = LoggerFactory.getLogger(RedisRepository.class);19

20 @Autowired21 private RedisTemplateredisTemplate;22

23 //----------------String-----------------------

24 public voidsetKey(String key,String value){25 redisTemplate.opsForValue().set(key, value);26 }27

28

29 //----------------list----------------------

30 public Long lpush(String key, String val) throwsException{31 log.info("UDP Msg保存至redis中,key:" + key + ",val:" +val);32 returnredisTemplate.opsForList().leftPush(key, val);33 }34

35 public String rpop(String key) throwsException {36 returnredisTemplate.opsForList().rightPop(key);37 }38

39 }

使用springframework框架中的RedisTemplate类去链接redis,此处是将收到的UDP消息左保存(lpush)至list链表中,然后右边弹出(rpop)。

UdpRepository.java

1 packagecom.example.demo.repository.mysql;2

3 importcom.example.demo.mod.UdpRecord;4 importorg.springframework.data.jpa.repository.JpaRepository;5

6 /**

7 * Created by wj on 2017/8/31.8 */

9 public interface UdpRepository extends JpaRepository{10

11 }

定义Spring Data JPA接口,链接数据库。

其中

UdpRecord.java

1 packagecom.example.demo.mod;2

3 importjavax.persistence.Entity;4 importjavax.persistence.GeneratedValue;5 importjavax.persistence.Id;6 importjavax.persistence.Table;7 importjava.sql.Timestamp;8

9 /**

10 * Created by wj on 2017/8/31.11 *12 * 用来记录接收的UDP消息的日志13 */

14 @Entity15 @Table16 public classUdpRecord {17

18 private longid;19 privateString udpMsg;20 privateTimestamp time;21

22 @Id23 @GeneratedValue24 public longgetId() {25 returnid;26 }27

28 public void setId(longid) {29 this.id =id;30 }31

32 publicString getUdpMsg() {33 returnudpMsg;34 }35

36 public voidsetUdpMsg(String udpMsg) {37 this.udpMsg =udpMsg;38 }39

40 publicTimestamp getTime() {41 returntime;42 }43

44 public voidsetTime(Timestamp time) {45 this.time =time;46 }47 }

注解@Entity和@Table辨明这是一个实体类表格 ,其中的@Id和@GeneratedValue表明id是key值并且是自动递增的。

9)线程池的相关信息

TaskExecutePool.java

1 packagecom.example.demo.thread;2

3 importcom.example.demo.init.SysConfig;4 importorg.springframework.beans.factory.annotation.Autowired;5 importorg.springframework.context.annotation.Bean;6 importorg.springframework.context.annotation.Configuration;7 importorg.springframework.scheduling.annotation.EnableAsync;8 importorg.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;9

10 importjava.util.concurrent.Executor;11 importjava.util.concurrent.ThreadPoolExecutor;12

13 /**

14 * Created by wangjian on 2017/8/29.15 */

16 @Configuration17 @EnableAsync18 public classTaskExecutePool {19

20 @Autowired21 privateSysConfig config;22

23 @Bean24 publicExecutor myTaskAsyncPool() {25 ThreadPoolTaskExecutor executor = newThreadPoolTaskExecutor();26 executor.setCorePoolSize(config.getCorePoolSize());27 executor.setMaxPoolSize(config.getMaxPoolSize());28 executor.setQueueCapacity(config.getQueueCapacity());29 executor.setKeepAliveSeconds(config.getKeepAliveSeconds());30 executor.setThreadNamePrefix("MyExecutor-");31

32 //rejection-policy:当pool已经达到max size的时候,如何处理新任务33 //CALLER_RUNS:不在新线程中执行任务,而是由调用者所在的线程来执行

34 executor.setRejectedExecutionHandler(newThreadPoolExecutor.CallerRunsPolicy());35 executor.initialize();36 returnexecutor;37 }38 }

10)配置文件SysConfig.java

1 packagecom.example.demo.init;2

3 importorg.springframework.boot.context.properties.ConfigurationProperties;4 importorg.springframework.stereotype.Component;5

6 /**

7 * Created by wj on 2017/8/30.8 */

9 @Component10 @ConfigurationProperties(prefix="sysfig")11 public classSysConfig {12 private int UdpReceivePort;//UDP消息接收端口13

14 //线程池信息

15 private intCorePoolSize;16

17 private intMaxPoolSize;18

19 private intKeepAliveSeconds;20

21 private intQueueCapacity;22

23 public intgetCorePoolSize() {24 returnCorePoolSize;25 }26

27 public void setCorePoolSize(intcorePoolSize) {28 CorePoolSize =corePoolSize;29 }30

31 public intgetMaxPoolSize() {32 returnMaxPoolSize;33 }34

35 public void setMaxPoolSize(intmaxPoolSize) {36 MaxPoolSize =maxPoolSize;37 }38

39 public intgetKeepAliveSeconds() {40 returnKeepAliveSeconds;41 }42

43 public void setKeepAliveSeconds(intkeepAliveSeconds) {44 KeepAliveSeconds =keepAliveSeconds;45 }46

47 public intgetQueueCapacity() {48 returnQueueCapacity;49 }50

51 public void setQueueCapacity(intqueueCapacity) {52 QueueCapacity =queueCapacity;53 }54

55 public intgetUdpReceivePort() {56 returnUdpReceivePort;57 }58

59 public void setUdpReceivePort(intudpReceivePort) {60 UdpReceivePort =udpReceivePort;61 }62 }

11)小结

其实发送UDP和接收UDP消息的核心代码很简单,只是netty框架将其包装了。

UDP发送消息是

1 byte[] buffer =...2 InetAddress address = InetAddress.getByName("localhost");3

4 DatagramPacket packet = newDatagramPacket(5 buffer, buffer.length, address, 9999);6 DatagramSocket datagramSocket = newDatagramSocket();7 datagramSocket.send(packet);

udp接收消息是

1 DatagramSocket datagramSocket = new DatagramSocket(9999);2

3 byte[] buffer =....4 DatagramPacket packet = newDatagramPacket(buffer, buffer.length);5

6 datagramSocket.receive(packet);

看起来是不是很简单???

12)源代码下载地址

这里只公布了一个框架,其他很多部分由于涉及到了工作内容不便公布。

有需要的同学可以自行下载对其代码进行更改。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/574135.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

1-4 TCP/IP协议族

网络协议是在内核中实现的&#xff0c;socket是对tcp/ip协议的系统调用&#xff0c;提供以下两点功能&#xff1a; 1. 将应用撑血数据从用户缓冲区中复制到TCP/UDP内核发送缓冲区&#xff0c;以交付内核发送来的数据&#xff08;比如send&#xff09;&#xff0c;或者从内核TCP…

python将数据写入excel_【Python】将数据库中的数据查询出来自动写入excel文档

近期每天都要监控一个数据。第一个版本是这样的&#xff1a;每天新增一个文档来汇总这个数据。这样搞了几天之后&#xff0c;过了一个周末&#xff0c;过来突然发现数据变多了很多&#xff0c;这个时候要调整策略&#xff0c;直接一个文档汇总出要的数据就可以了。这样查了两天…

OC 继承

一、基本概念 程序的世界和人类的“对象”世界在思想上是没有设么区别的&#xff0c;富二代继承了父母&#xff0c;自然就拥有了父母拥有的所有资源&#xff0c;子类继承了父类同样就拥有了父类所有的方法和属性&#xff08;成员变量&#xff09;。 在这里动物是猫类和狗类的父…

吃西瓜 最大子矩阵 三维的。 rqnoj93

真的好苦逼&#xff0c;这道神题&#xff0c;交了几十次都是70分&#xff0c;剩下的都TLE了&#xff0c;崩溃。 没办法&#xff0c;只能这样了。在网上看了别人的算法&#xff0c;大概思想是把三维的先压成两维&#xff0c;再把二维的弄成一维&#xff0c;这样就很容易了。 首先…

mysql 两张表差集_mysql中两张表使用left join on 求差集详解

1.表结构mysql> select * from allStudents;-----------| id | name |-----------| 1 | ???? || 2 | ???? || 3 | ???| 4 | four |-----------4 rows in set (0.00 sec)mysql> select * from currentStudents;------------| id | name |------------| 1 | luo…

Android 高级UI设计笔记08:Android开发者常用的7款Android UI组件(转载)

Android开发是目前最热门的移动开发技术之一&#xff0c;随着开发者的不断努力和Android社区的进步&#xff0c;Android开发技术已经日趋成熟&#xff0c;当然&#xff0c;在Android开源社区中也涌现了很多不错的开源UI项目&#xff0c;它们可以帮助Android开发者更方便快捷地完…

centos linux怎么安装mysql_CentOS-Linux系统下安装MySQL

一、mysql的安装Yum(全称为 Yellow dog Updater, Modified)是一个在Fedora和RedHat以及CentOS中的Shell前端软件包管理器。基于RPM包管理&#xff0c;能够从指定的服务器自动下载RPM包并且安装&#xff0c;可以自动处理依赖性关系&#xff0c;并且一次安装所有依赖的软件包&…

Operating System-进程/线程内部通信-临界区(Critical Regions)

上一篇文章讲述了进程之间的竞争条件&#xff1a;多个进程同时进入一个共享区域&#xff0c;导致了数据的不一致&#xff0c;本文主要介绍如何解决这个问题。 一、临界区介绍 解决这个问题就是阻止多个进程同时进入这个共享区域&#xff0c;换句话说&#xff0c;进程之间针对这…

centos命令行安装mysql_Centos下安装mysql 总结

一、MySQL安装二、MySQL的几个重要目录MySQL安装完成后不象SQL Server默认安装在一个目录&#xff0c;它的数据库文件、配置文件和命令文件分别在不同的目录&#xff0c;了解这些目录非常重要&#xff0c;尤其对于Linux的初学者&#xff0c;因为 Linux本身的目录结构就比较复杂…

乘法逆元模板

1.扩展欧几里得求逆元 typedef long long ll;//ax by gcd(a,b) //传入固定值a,b.放回 dgcd(a,b), x , y void extendgcd(ll a,ll b,ll &d,ll &x,ll &y) {if(b0){da;x1;y0;return;}extendgcd(b,a%b,d,y,x);y-x*(a/b); }//Ax1(mod M)&#xff0c;gcd(A,M)1 //输入&…

【html】【19】高级篇--大事件时间轴

下载:  http://sc.chinaz.com/jiaoben/131112181390.htm 其它:  http://sc.chinaz.com/tag_jiaoben/shijianzhou.html 效果:   html 代码: 1 <!DOCTYPE html>2 <html>3 <head>4 <meta http-equiv"Content-Type" content"text/html; …

必须声明标量变量_Excel VBA解读(136): 在用户定义函数中的变体、引用、数组、计算表达式、标量...

学习Excel技术&#xff0c;关注微信公众号&#xff1a;excelperfect在前面的几篇文章中&#xff0c;我们自定义的函数使用定义为Range的参数来从Excel工作表中获取数据&#xff0c;例如&#xff1a;Function VINTERPOLATEB(Lookup_Value As Variant, _Table_Array As Range, _C…

HTMl5的存储方式sessionStorage和localStorage详解

html5中的Web Storage包括了两种存储方式&#xff1a;sessionStorage和localStorage。sessionStorage用于本地存储一个会话&#xff08;session&#xff09;中的数据&#xff0c;这些数据只有在同一个会话中的页面才能访问并且当会话结束后数据也随之销毁因此sessionStorage不是…

mysql5.7四字节中文_mysql 字节问题,中文和数字

在mysql 5.1.5-alpha下测试得出如下结论latin1:1character1byte, 1汉字2character,也就是说一个字段定义成 varchar(200)&#xff0c;则它可以存储100个汉字或者200个字母。这一点要注意&#xff0c;尤其是当字段内容是字母和汉字组成时&#xff0c;尽量假设字段内容都是由汉字…

mysql 主主忽略错误_MySQL 主主报错: Fatal error: The slave I/O thread stops because master and slave have...

Mysql 主主启动错误处理error 信息&#xff1a;Slave_IO_State:Master_Host: 192.168.6.87Master_User: replicationMaster_Port: 3306Connect_Retry: 60Master_Log_File: mysql-bin.000003Read_Master_Log_Pos: 106Relay_Log_File: mysqld-relay-bin.000002Relay_Log_Pos: 4Re…

mysql内部_MySQL SQL语句内部剖析

一条SQL在MySQL体系结构内的执行流程:注意只有查询操作才会走查询缓存&#xff0c;而表的结构和数据发生改变时将会清空查询缓存。所以开启查询缓存的意义不大&#xff0c;8.0后已经废弃了该功能。一条update在存储引擎内部的执行步骤如下:SQL:update t set cc1 where id2;SQL完…

用Backbone.js创建一个联系人管理系统(四)

原文: Build a Contacts Manager Using Backbone.js: Part 4 这一系列教程的第四部分,教我们如何完成对已经存在的Contacts进行编辑和保存. 本教程是基于这一系列的前三个教程. 有不清楚的请先阅读前三部分. 开始 在Contact原模版里添加一个edit按钮. <button class"ed…

mysql默认时间怎么不同步_MYSQL 更新时间自动同步与创建时间默认值共存问题

本文作者&#xff1a;苏生米沿在使用SQL的时候&#xff0c;希望在更新数据的时候自动填充更新时间&#xff0c;那么在mysql中是如何实现的呢&#xff1f;如创建表usersCREATE TABLE RS_SIGNUPUSER (ID VARCHAR(36) COMMENT 主键(业务功能无关),USERNAME VARCHAR(50) COMMENT 姓…

HOJ-2662Pieces Assignment(状态压缩,动态规划)

Pieces Assignment Source : zhouguyue Time limit : 1 sec Memory limit : 64 M Submitted : 415, Accepted : 149 Background 有一个n*m的棋盘(n、m≤80,n*m≤80)要在棋盘上放k(k≤20)个棋子&#xff0c;使得任意两个棋子不相邻&#xff08;每个棋子最多和周围4个棋子相…

python代码技巧_让你python代码更快的3个小技巧

大家好&#xff01;今天呢&#xff0c;我们来聊一聊如何加速你的 python 代码。Python 语言的优点可以列举出许多&#xff0c;语法简单易懂、模块丰富、应用广泛等等。但是世界上没有有完美的东西&#xff0c;python 一个明显缺点就是运行速度慢&#xff0c;至少跟 C 语言没法比…