目录
1. QSPI是什么?
1. QSPI是什么? SPI协议其实是包括:Standard SPI、Dual SPI和Queued SPI三种协议接口,分别对应3-wire, 4-wire, 6-wire。
(1)通常我们说的SPI就是Standard SPI,有4根信号线,分别为CLK、CS、MOSI和MISO。数据线工作在全双工。
(2)Dual SPI,它只是针对SPI Flash而言,不是针对所有SPI外设。对于SPI Flash,全双工并不常用,因此扩展了mosi和miso的用法,让它们工作在半双工,用以加倍数据传输。也就是对于Dual SPI Flash,可以发送一个命令字节进入dual mode,这样mosi变成SIO0(serial io 0),mosi变成SIO1(serial io 1),这样一个时钟周期内就能传输2个bit数据,加倍了数据传输。
(3)类似的,还可以扩展,与也是针对SPI Flash,Qual SPI Flash增加了两根I/O线(SIO2,SIO3),目的是一个时钟内传输4个bit
而QSPI就是Queued SPI的简写。
2. 接口问题 上图是某SPI FLASH的引脚接口示意图,它即支持SPI通信,也可以使用DSPI通信或者QSPI通信,
这块芯片一共有8个有用的管脚,其每个管脚的功能定义如下:
每个引脚的详细描述如下:
1、Chip Select(/CS)
片选信号Chip Select(/CS)的作用是使能或者不使能设备的操作,当CS为高时,表示设备未被选中,串行数据输出线(DO或IO0,IO1,IO2,IO3)均处于高阻态,当CS为低时,表示设备被选中,FPGA可以给QSPI Flash发送数据或从QSPI Flash接收数据。
2、串行数据输入信号DI以及串行输出信号DO
标准的SPI协议在串行时钟信号(SCLK)的上升沿把串行输入信号DI上的数据存入QSPI Flash中,在串行时钟信号(SCLK)的下降沿把QSPI Flash中的数据串行化通过单向的DO引脚输出。而在Dual SPI与Quad SPI中,DI与DO均为双向信号(既可以作为输入,也可以作为输出)。
3、Write Project(/WP)
写保护信号的作用是防止QSPI Flash的状态寄存器被写入错误的数据,WP信号低电平有效,但是当状态寄存器2的QE位被置1时,WP信号失去写保护功能,它变成Quad SPI的一个双向数据传输信号。
4、HOLD(/HOLD)
HOLD信号的作用是暂停QSPI Flash的操作。当HOLD信号为低,并且CS也为低时,串行输出信号DO将处于高阻态,串行输入信号DI与串行时钟信号SCLK将被QSPI Flash忽略。当HOLD拉高以后,QSPI Flash的读写操作能继续进行。当多个SPI设备共享同一组SPI总线相同的信号的时候,可以通过HOLD来切换信号的流向。和WP信号一样,当当状态寄存器2的QE位被置1时,HOLD信号失去保持功能,它也变成Quad SPI的一个双向数据传输信号。
5、串行时钟线
串行时钟线用来提供串行输入输出操作的时钟。
3. QSPI的使用 3.1 工作模式 该接口可以在以下三种模式下工作:
① 间接模式:使用 QSPI 寄存器执行全部操作
什么是虚拟机呢?对平常不怎么接触电脑网络这块的,对于虚拟机这块肯定是不太了解的,虚拟机能够带来很多方便,今天来讲解下什么是虚拟机,虚拟机能做到什么
虚拟机英文名(Virtual Machine)是通过软件模拟的完整计算机系统。在实体计算机中能够完成的工作在虚拟机中都能够实现。在计算机中创建虚拟机时,需要将实体机的部分硬盘和内存容量作为虚拟机的硬盘和内存容量。每个虚拟机都有独立的CMOS、硬盘和操作系统,可以像使用实体机一样对虚拟机进行操作。
使用虚拟机的好处 1.如果要在一台电脑上装多个操作系统,不用虚拟机的话,有两个办法:一是装多个硬盘,每个硬盘装一个操作系统。这个方法比较昂贵。二是在一个硬盘上装多个操作系统。这个方法不够安全,因为硬盘MBR是操作系统的必争之地,搞不好会几个操作系统同归于尽。
2.虚拟机可以在一台机器上同时运行几个操作系统,是SOHO开发一族的必备工具。有了虚拟机,在家里只需要一台电脑,或出差时只带着一个笔记本,就可以调试C/S、B/S的程序了。
3.利用虚拟机可以进行软件测试。
缺点:它就是建立在主机上,毕竟是虚拟机,也是文件,很容易被破坏。
使用虚拟机的硬件要求 虚拟机毕竟是将两台以上的电脑的任务集中在一台电脑上,所以对硬件的要求比较高,主要是CPU、硬盘和内存。目前的电脑CPU多数是PIII以上,硬盘都是几十G,这样的配置已经完全能满足要求。关键是内存。内存的需求等于多个操作系统需求的总和。现在的内存已经很便宜,也不成为问题了。现在的高防服务器也是可以开虚拟化的,非常的方便。
目录:
一、边沿检测
二、串并转换
三、分频器
四、异步复位同步释放
五、序列信号产生器
六、序列检测器
七、双端口RAM
八、同步FIFO
九、异步FIFO
常见电路系列连接:
CSDNhttps://mp.csdn.net/mp_blog/creation/editor/122940873CSDNhttps://mp.csdn.net/mp_blog/creation/editor/122991113七、双端口RAM
module dualram#( parameter ADDR_WIDTH = 4, DATA_WIDTH = 8, DATA_DEPTH = 8 )( input rd_clk, input wr_clk, input rst_n, //port a input wr_en, input [3:0] wr_addr, input [7:0] wr_data, //port b input rd_en, input [3:0] rd_addr, output reg [7:0] rd_data ); reg [DATA_WIDTH-1:0] register [DATA_DEPTH-1:0]; integer i; always@(posedge wr_clk or negedge rst_n) if(~rst_n)begin for(i=0;i<DATA_DEPTH;i=i+1)begin register[i]<='h0; end end else if(wr_en) register[wr_addr]<=wr_data; always@(posedge rd_clk or negedge rst_n) if(~rst_n) rd_data<='h0; else if(rd_en) rd_data<=register[rd_addr]; endmodule 仿真代码
调出项目属性界面 在项目上点击右键,选择Properties(属性)页面。
选择Debug属性 选中Debug分项中的General后点击Open debug launch profiles UI链接。
启用本地代码调试 选择Enable native code debugging启用本地代码调试。
如果参数类型所对应的实例在spring容器中只有一个,则默认选择这个实例。如果有多个,则需要根据参数名称来选择(参数名称就相当于是spring的配置文件中的bean的id)
如:
@Bean public ConnectionFactory connectionFactory1() { CachingConnectionFactory cachingConnectionFactory = new CachingConnectionFactory(); cachingConnectionFactory.setHost("xxxx"); cachingConnectionFactory.setUsername("xxxx"); cachingConnectionFactory.setPassword("xxxx"); cachingConnectionFactory.setPort(111); return cachingConnectionFactory; } @Bean public ConnectionFactory connectionFactory2() { CachingConnectionFactory cachingConnectionFactory = new CachingConnectionFactory(); cachingConnectionFactory.setHost("ttt"); cachingConnectionFactory.setUsername("ttt"); cachingConnectionFactory.setPassword("ttt"); cachingConnectionFactory.setPort(111); return cachingConnectionFactory; } @Bean public SimpleRabbitListenerContainerFactory bookingContainerFactory(SimpleRabbitListenerContainerFactoryConfigurer configurer, ConnectionFactory connectionFactory1) { SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory(); factory.setPrefetchCount(5); factory.setConcurrentConsumers(5); configurer.configure(factory, connectionFactory1); return factory; } 如上:定义2个connection,在SimpleRabbitListenerContainerFactory的最后一个参数里面,ConnectionFactory connectionFactory1 。
先按照类型ConnectionFactory查找,发现有2个相同类型的ConnectionFactory., connectionFactory1 和connectionFactory2。接着就按照参数名字查找
这里指定的参数名字是connectionFactory1,就使用connectionFactory1这个bean.
若是使用的是:ConnectionFactory connectionFactory2,就使用的connectionFactory2这个bean.
如果参数名字是其他的不存在的bean,此时只能按照之前的类型来找,由于有2个相同类型的实例,所以会报错
————————————————
版权声明:本文为CSDN博主「EmineWang」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
#include <stdio.h> #include <stdlib.h> void yrCalc(long int,int*,int*,int*); int main(int argc, char *argv[]) { long int number; int year,month,day; //inpput printf("Pleaese input the total numbers of days from the date 1/1/1900\n"); scanf("%d",&number); //call the function yrCalc(number,&year,&month,&day); //output printf("%d/%d/%d\n",year,month,day); system("pause"); return 0; } void yrCalc(long int number,int*year,int*month,int*day){ *year=1900+number/360; *month=1+(number-(number/360)*360)/30; *day=1+(number-(number/360)*360-((number-(number/360)*360)/30)*30); } (按照每月30天每年360天计算)
感谢非凡让我蹭他的红帽课程!!! rhce day01 首先要学习连接X-shell,那么就要对环境进行配置 需要设置ip地址,所需知识如下:
[root@server1 ~]# ifconfig 查看ip地址
有四个ip地址,分别为bro桥接网络,ens33以太网,lo环回网,virbro虚拟桥接网;需要用到的是ens33 ens33是我们所要进行操作的网卡 nmtui 文本方式配置ip地址
给ens33配置ip地址,发现网卡不在其中
nmcli connection add con-name ens33 ifname ens33 type ethernet 将设置以太网ens33网卡添加到虚拟机中
给ens33配置ip地址
将配置方式改为手工
ip地址要和真机使用的ip地址为同一网段,所以在设置了虚拟机要连接到的本机虚拟网卡后,要找到本机中的虚拟网卡,查看ip地址。查看真机中的虚拟网卡
然后给ens33配置ip地址 激活ens33网卡 配置网ip地址后Activate a connection 补充:可通过Vmware中的编辑中的虚拟网络编辑器来查看虚拟机设置中的自定义特定虚拟网络 VMnet1就等于真机有一个名为VMnet1的虚拟网卡,实现了与ens33rhel同网段互通操作完成后ping一下 day02配置red虚拟器中的ip地址 (EX200-练习题中第一题) 先打开rhel中的虚拟机red,打开方式有两种,
一种是命令行打开:[root@server1 ~]# virt-manager
另一种是在图形化界面中打开将red中的配置清空
[root@server1 ~]# rht-vmctl reset red配置ip地址等一系列,最后要选中开机自启,选中Automatically connect,空格出现X表示选中配置完后查看 [root@red ~]# hostnamectl set-hostname red.net0.example.com //设置固定主机名 [root@red ~]# nmcli connection show //找出网卡对应的连接名 [root@red ~]# nmcli connection modify "网卡名" ipv4.method manual ipv4.addresses 172.25.0.25/24" ipv4.
直连路由:
使用路由器连接不同网段:
[Huawei]undo info-center enable //关日志
[Huawei]interface gigabitEthernet0/0/0 //进入0号接口
[Huawei-GigabitEthernet0/0/0]ip address 192.168.1.254 24 //配置ip
[Huawei-GigabitEthernet0/0/0]in g0/0/1
[Huawei-GigabitEthernet0/0/1]ip address 192.168.2.254 24
[Huawei]display ip interface brief //检查设备所有的ip地址配置情况之后每个pc再配置对应网段的网关即可全网互通
[Huawei]display ip routing-table //检查路由表
ICMP internet控制报文协议,可以反馈网络中比如是否联通,花费时间等信息
Ping -t 持续ping
Ping -l 1000 将ping包大小修改为1000字节
路由器是依靠路由表转发数据
路由表的产生方式:
1, 直连路由,路由器接口配置好ip并开启则自动产生
2, 静态路由,由管理员手工配置,添加所要前往的地址
语法格式:ip route-static 目标网段地址 子网掩码 下一跳
静态路由:
第一台路由器:
[Huawei]ip route-static 192.168.3.0 24 192.168.2.2 //添加静态路由
使该路由设备可以前往3网段,下一跳地址是2.2
[Huawei]ip route-static 192.168.4.0 24 192.168.2.2
[Huawei]display ip routing-table | include /24 //查看路由表,已经
pycharm使用ssh连接服务器(ubuntu)跑代码报错:“sudo+ssh: ……bash: line 0: cd: xxx/code: No such file or directory” sudo+ssh://xxx@xxx/anaconda3/envs/py36/bin/python -u “xxx/code/main.py”
bash: line 0: cd: xxx/code: No such file or directory
SudoPasswordPrompt655neudrfcn7scuc
目测应该是pycharm的bug,解决方法如下:
File -> Settings-> Project: (你的项目名称) -> Python Interpreter
点击如下图所示的设置按钮:
点Show All…,会出现下图:
在这里面删除一些与当前项目不相关的解释器就可以了
常见电路系列连接
https://blog.csdn.net/weixin_40634481/article/details/122940873?spm=1001.2014.3001.5501https://blog.csdn.net/weixin_40634481/article/details/122940873?spm=1001.2014.3001.5501
目录:
一、边沿检测
二、串并转换
三、分频器
四、异步复位同步释放
五、序列信号产生器
六、序列检测器
四、异步复位同步释放
上来先来三个问题
问题一:为什么要用异步复位同步释放?
答:这个问题要从同步复位和异步复位优缺点来解释,异步复位的缺点是其可能会引起亚稳态,同步复位的缺点是需要消耗较多的资源优点是降低了亚稳态出现的概率,而异步复位同步释放即保留了异步复位的功能,又避免了异步复位释放时所面临的recovery或者removal违例的问题。
问题二:异步复位同步释放是怎么工作的?
答:
我的理解就是单比特数据通过打拍的方式来降低亚稳态发生的概率,当rst_async_n信号有效时第二个触发器的输出为低电平,复位有效,如果rst_async_n信号释放时刚好在clk上升沿,则第一个触发器的输出可能是亚稳态,通过打一拍的方式可以降低亚稳态的概率(关于亚稳态的问题计划到后面会详细总结一篇文章)
问题三:为什么触发器的输入端直接给1'b1而不是复位信号?
答:这样也是为了节省资源,减少了一个反相器。
always@(posedge clk or negedge rst_async_n) if(~rst_n)begin rst_n_d1 <= 1'b0; rst_n_d2 <= 1'b0; end else begin rst_n_d1 <= 1'b1; rst_n_d2 <= rst_n_d1; end assign rst_sync_n=rst_n_d2; 五、序列信号产生器
module sequence_gen( input clk, input rst_n, output reg dout ); localparam [4:0] s0=5'b00001, s1=5'b00010, s2=5'b00100, s3=5'b01000, s4=5'b10000; reg [4:0] state,next_state; always@(posedge clk or negedge rst_n) if(~rst_n) state<=s0; else state<=next_state; always@(*) case(state) s0:next_state=s1; s1:next_state=s2; s2:next_state=s3; s3:next_state=s4; s4:next_state=s0; default:next_state=s0; endcase always@(posedge clk or negedge rst_n) if(~rst_n) dout<=1'b0; else case(next_state) s0:dout=1'b0; s1:dout=1'b0; s2:dout=1'b1; s3:dout=1'b0; s4:dout=1'b1; endcase endmodule 仿真代码
相关阅读 Spring AOP基础组件 AdviceSpring AOP基础组件 AdvisorSpring AOP基础组件 AopProxySpring AOP基础组件 AopProxyFactory 简介 使用AOP代理对象包装有资格的Bean的BeanPostProcessor实现,再调用Bean之前会委派给特定的拦截器;
AbstractAutoProxyCreator会区分两种拦截器:
通用拦截器,被所有它创建的代理所共享,通过interceptorNames属性配置,可以没有;特定拦截器,只应用于特定的Bean实例; 继承自ProxyProcessorSupport,具有ProxyConfig中动态代理相关的配置属性;
实现了SmartInstantiationAwareBeanPostProcessor接口,实现了实例化前后置处理,属性的后置处理;
拦截器都是通过Bean name而不是Bean 引用进行配置,这方便正确地处理多例类型的Advisor、Interceptor;
子类可以重写判断Bean是否可以被代理的策略,比如:根据类型,根据Bean name,根据BeanDefinition等;也可以添加额外的拦截器;
源码 public abstract class AbstractAutoProxyCreator extends ProxyProcessorSupport implements SmartInstantiationAwareBeanPostProcessor, BeanFactoryAware { // 表示不代理 @Nullable protected static final Object[] DO_NOT_PROXY = null; // 表示无特定拦截器 protected static final Object[] PROXY_WITHOUT_ADDITIONAL_INTERCEPTORS = new Object[0]; // 默认是GlobalAdvisorAdapterRegistry private AdvisorAdapterRegistry advisorAdapterRegistry = GlobalAdvisorAdapterRegistry.getInstance(); // 通用拦截器的Bean name,默认无通用拦截器 private String[] interceptorNames = new String[0]; // 通用拦截器是否在特定拦截器之前应用标识,默认为true private boolean applyCommonInterceptorsFirst = true; @Override @Nullable public Class<?
1:JDK下载 根据自己的要求下载不同版本的JDK
Java Downloads | Oracle
Windows/Linux/macOS选择和自己系统一致即可。
2:安装 下载后,安装时一直下一步,如果需要更改jdk安装路径注意一下即可。(需要记住安装路径,后续配置环境需要)
默认路径是C:\Program Files
C:\Program Files:对应64位软件
C:\Program Files(X86):对应32位软件
3:环境配置 JDK8为例:
① 右击此电脑->高级系统设置->高级->环境变量
②注意是系统变量(不是用户变量)
③新建 变量名:JAVA_HOME 变量值为jdk的安装路径
④ 找到名为path的变量,编辑,将jdk中bin的路径复制
⑤新建 变量名:CLASSPATH 变量值为
.;%JAVA_HOME%\lib\dt.jar;%JAVA_HOME%\lib\tools.jar
这里的%JAVA_HOME%就是刚才JDK的安装路径
⑥win+R 输入cmd
输入 java -version
4问题: JDK下载安装完成后: 包含两个JDK和JRE(如果没有JRE也不要紧,在JDK里面也会有JRE)
如果本次安装后,下次重启电脑JDK失效,则将CLASSPATH 变量值中的%JAVA_HOME%改为jdk的安装路径。
一、Makefile 1.1.问:如果项目产品代码有1万源文件.c,编译极其的繁琐
gcc -o main main.c a.c b.c .... 一个万.c
这么简化程序的编译呢?
答:必须只能利用Makefile来实现
1.2.Makefile功能:能够制定编译规则,将来让gcc编译器根据这个规则来编译程序,Makefile本质就是一个文本文件,此文件给make命令使用,将来make命令会根据Makefile里面的编译规则让gcc编译程序。
1.3.Makefile语法格式:
目标:依赖1 依赖2 依赖3 ....依赖N
(TAB键)编译命令1
(TAB键)编译命令2
...
(TAB键)编译命令N
(TAB键) 还可以是其他命令:ls/cp/cd等
注意:Makefile注释用#
例如:目标是把helloworld.c编译生成helloworld
vim Makfile 添加
#指定规则:一步到位
helloworld:helloworld.c
gcc -o helloworld helloworld.c #或者
#指定规则1:分步
helloworld:helloworld.o
gcc -o helloworld helloworld.o
#指定规则2:
helloworld.o:helloworld.c
gcc -c -o helloworld.o helloword.c
案例:利用Makefile编译helloworld.c文件
vim helloworld.c
vim Makefile
make //编译程序
./helloworld
make //编译提示helloworld是最新的
vim helloworld.c //修改源文件
ls -lh //查看helloworld.c和helloworld的时间戳
make //又重新编译
先检查有没有helloworld文件,如果有,就检查helloworld.c文件的时间戳是不是比他新,如果helloworld.c文件比helloworld文件新,就重新编译,反之不更新,如果没有helloworld文件,就按编译规则来。
1.4.Makefile工作原理
一、生成ssh公钥
step1:安装GIT和TortoiseGit.
step2:文件夹空白地方右键点击 Git Bash Here 进入终端。
如果右键没有Git Bash Here,操作方法见 https://mp.csdn.net/mp_blog/creation/editor/122945834
step3:执行cd ~/.ssh/ 进入 .ssh 文件夹,如果没有.ssh文件夹,可以执行mkdir ../.ssh创建.ssh文件夹。
step4:配置git,分别执行
git config --global user.name "你的名字"
git config --global.email "你的邮箱"
step5:执行完后在以下命令生成ssh key
ssh-keygen -t rsa -C “你的邮箱”
然后一直回车
step6:上述命令执行完后,到C:\Users\xiongqingqing\.ssh文件夹下可以看到id_rsa和id_rsa.pub
两个文件。
step7:登录GitLab管理平台
再点击SSH keys
将id_rsa.pub文件内容复制到Key
二、生成ppk文件
step7:下载PuTTY,安装后点击puttygen.exe
step8:点击Key,然后点击Parameters for saving key files
将ppk文件版本改成2(否则会报Couldn’t load private key (PuTTY key format too new))
step9:设置完后,再点击Conversions,再点击Import key,将之前生成的id_rsa文件导入
step10:导入后点击Save private key生成ppk文件
step11:然后git clone的时候将Load Putty Key设置为刚刚生成的ppk文件即可。
至此,就可以正常拉取代码了。
计划将常见电路的verilog实现进行总结,如有不对的地方,欢迎大家批评指正,先放目录
一、边沿检测
二、串并转换
三、分频器
一、边沿检测
首先对数据打两拍,然后通过两拍数据之间的逻辑关系来判断出是上升沿还是下降沿
module edge_detect( input clk, input rst_n, input data, output pos_edge, output neg_edge ); reg data_d0,data_d1; always@(posedge clk or negedge rst_n) if(~rst_n)begin data_d0 <= 'h0; data_d1 <= 'h0; end else begin data_d0 <= data; data_d1 <= data_d0; end assign pos_edge = data_d0 && ~data_d1; assign neg_edge = ~data_d0 && data_d1; endmodule 仿真代码
module tb_edge_detect(); parameter PERIOD = 10; bit clk; reg rst_n; reg data; wire pos_edge; wire neg_edge; always #(PERIOD/2) clk = ~clk; initial begin rst_n=1'b1; #20; rst_n=1'b1; @(posedge clk); data=1'b1; #40; data=1'b0; #40; data=1'b1; #40; end edge_detect u_edge_detect( .
1)强引用(Strong Reference):Object obj = new Object();强引用的对象,GC回收器永远都不会回收掉这些被引用的对象。
2)软引用(Soft Reference):描述的是一些还有用但非必需的对象。在系统将会发生内存溢出之前,会把这些对象列入回收范围进行二次回收,也就是说系统将会发生内存溢出了,才会对他们进行回收。
3)弱引用(Weak Reference):程度比软引用更弱一些。这些对象只能生存到下次 GC 之前。当 GC 工作时扫描到,无论内存是否足够都会将其回收。
4)虚引用(Phantom Reference):一个对象是否存在虚引用,完全不会对其生存时间构成影响。如果一个对象存在虚引用,在这个对象被回收之前,它的虚引用会被添加到引用队列中去,也就是在引用队列中看到了这个对象的虚引用,就表示这个对象即将被回收,可以做一些回收之前的必要工作。
阻塞赋值“=”对应组合逻辑电路赋值(无存储功能,立即赋值),并且会阻塞后面的赋值操作,
非阻塞赋值“<=”对应时序逻辑电路赋值(有存储功能),所有非阻塞赋值操作在同一时刻进行赋值。
下面分别通过vivado综合不同情况赋值的代码。
第一种:在时序逻辑电路中使用阻塞赋值,通过综合后的电路可以看出非阻塞赋值综合出来的电路时立即执行赋值操作,和组合逻辑电路特性一致,无缓存功能,out_o直接被优化掉了。
always@(posedge clk or negedge rst_n) if(~rst_n)begin out_o <= 'h0; out_o_1 <= 'h0; end else if(a_i)begin out_o = b_i; out_o_1 = out_o; end 第二种:在时序逻辑电路中使用非阻塞赋值,通过综合后的电路可以看出非阻塞赋值综合出来的电路对应时序逻辑电路的特性,有缓存功能,out_o_1相较于out_o延迟一拍。
always@(posedge clk or negedge rst_n) if(~rst_n)begin out_o <= 'h0; out_o_1 <= 'h0; end else if(a_i)begin out_o <= b_i; out_o_1 <= out_o; end 在仿真中仿真器为了能正确模拟实际电路,规定当前时刻的事件是有优先级的:
活跃事件在当前时刻是立即执行的
其它事件是等待仿真进行到某个时刻是开始执行的。
为了不出现问题,平时建议规范书写代码,有以下几点:
1、时序电路用非阻塞;
2、组合电路用阻塞;
3、同一个always块中阻塞非阻塞不要混用(混用综合出来的电路可能不是你想要的)。
记得1954年秋天,袁萌在江苏南京第十中学学习生物学、达尔文的进化论,懂得了优胜劣汰的道理。
希尔伯特几何基础就是数学发展史的进化结果,我们相信在未来50年的时间内,希尔伯特几何基础的创新思想不会被淘汰。
为此,我们将该书的有关章节内容(全文)刊登在我们的网站上。《希尔伯特几何基础》
内容如下:
几何基础序言 伟大的德国数学家希尔伯特为其代表作“几何基础”写的序言如下: 德文第七版的俄译本序言 • Foreword • 希尔伯特曾有一个学生,写了一篇论文来证明黎曼猜想,尽管 其中有个无法挽回的错误,希尔伯特还是被深深地吸引了。第二年, 这个学生不知道怎么回事死了,希尔伯特要求在葬礼上做一个演说。 那天,风雨瑟瑟,这个学生的家属们悲痛不已。希尔伯特开始致辞, 他首先指出:“这样的天才这么早离开我们, 实在是让人痛惜呀!” 众人同感,哭得越来越凶。接下来,希尔伯特说:“尽管这个学生的 证明有错,但是如果按照这条路走下去,应该有可能证明黎曼猜想。” 再接下来,希尔伯特冒着雨充满激情地讲道:“事实上,让我们考虑 一个单变量的复函数”众人皆倒。 德文第七版的俄译本序言 殛在 希尔伯特的《几何基础》和它在本问题 发展的历史中的地位* ;- .K.拉舍夫斯基 作为物理学的几何学 当我们学习几何学的时候,一开始——如同在中学里学习几何学时那样——就在我们的认识中产生了 独特的思维世界,它奇特地既是现实的又是幻想的。事实上,我们关于直线、平面、几何体(如球)等的论 述,是在给它们以完全确定的性质以后才进行的。然而具有作为我们研究对象的那种形状的东西,究竟在哪 里和在什么意义下存在着呢?我们岂不是都知道,不论我们如何地磨(譬如说)一块金属板的表面,由于工 具和动作本身的不可避免的偏差,我们永远不能把它磨成“理想平面”的形状。更何况不仅无法达到理想地 平的形状,而且根据物质的原子结构,甚至还不可能无限制地接近它哩!事实上,当我们加强所要求的精确 度时,金属板就将被分解成各别的原子,以致一般地所谓它的表面都无意义了。 而直线又是怎么样呢?或许可以认为光线是沿着理想的直线而传播的吧?然而量子力学告诉我们,光 线是利用各别的介质——量子——而传播的,至于说到这种量子在运动时所走的道路,一般地也没有意义。 那么,我们在几何学里究竟研究些什么呢?难道只研究与物质世界格格不入的幻想、我们想象力的创 造吗?可是从日常的经验和从技术上的实验,我们就能坚定地知道,对这些幻想的对象所推导出来的法则和 规律,都以不可克服的力量服从于物质的自然界;以致进行新的设计的工程师,当遭受失败时,可以怀疑其 任何的假设,而决不会怀疑诸如关于角柱体积的公式。 这些几何形象,看来好像是无足轻重的、非物质的,而同时却以不可克服的力量来刻画物质世界的,又 好像可以认为(如同唯心主义哲学经常如此说的)是上帝按其自己的意象创造的,究竟是些什么呢? 唯物主义的宇宙观帮助我们来回答这个问题。让我们特地从粗糙的例子开始。假设在我们面前有筑在 一块土地边上的一道围墙。如果我们要计算这块土地的面积,来拟定其规划,则在我们几何的计算里就将画 出一条封闭的曲线来代替围墙,而用它所分隔成的平面片段来代替土地。这种使用几何概念来暗中顶替物质 对象,其实质又何在呢? 问题是:不论我们是用木头还是石头来造围墙,不论我们造多宽多高,不论我们是否向旁边移动了这么 一厘米,等等,这块土地实际上并不因之而有所改变。由于我们所关心的只是土地本身,至于沿其边界究竟 造了些什么,实际上并不起任何作用,尽可以把所有这些都撇开不管。因此,我们抛弃了作为物体的围墙的、 在当前情况下对我们不重要的绝大多数的性质。围墙对我们重要的那些性质——与其长度方面的延伸性有关 的性质,才属于我们考虑之列,这些性质也就正是曲线在几何意义上的性质。有同样事实的各种各样的例子 是不胜枚举的:当我们讨论绳子、飞驰的炮弹的路线等时,则在一定的精确程度下,我们所必须关心的也只 是它们的那样一些性质,那就是我们称为几何曲线的性质。 总之,当我们研究几何曲线时,我们同时也就研究了土地的围墙,一定长度——与粗细相比——的绳子, 以及飞驰的炮弹的路线,然而对所有这些现象而言,我们并不在各方面都保留它们性质的多样性,因为它们 德文第七版的俄译本序言 殛在 并不具有最大的精确性,而只是就在当前的情况下对我们重要的一维延伸性方面来加以选择,并且也只具有 实用上必要的精确程度。于是我们叫做几何曲线的性质的这些对象的共同性质就显得突出了。这样,假如我 们说曲线没有宽度,那只不过是简短地表明,围墙的宽度实际上并不影响其所包围的土地,绳子的横截面的 大小与其长度相比可以略去不计,等等而已。 所有别的几何概念和命题也都有类似的意义。它们全都反映了物质对象的性质和物质世界的法则。它们 的“理想的”特性只是表明了在物体性质的已知联系中非主要的性质被抛弃(抽象),特别地是它们只以一 定的精确程度而被考虑。这种抽象可以用来清楚地揭露物体的共同而又深藏的性质,我们把它们叫做延伸的 性质而且在几何学里加以研究。几何法则之所以为自然界所必须,就由于它们是从自然界抽象出来的缘故。 这样一来,反映物质现实的几何真理,以简化了的和公式化了的形状,近似地重现了物质现实。正由于 抛弃了无穷多的复杂事实,才产生了几何理论的如此使人信服的严整性和合理性。而假如是如此的话,则很 自然地,就不能强求几何学[暂时谈到的总限于欧几里得(Euclid)几何学]无限制地恰当于研究物质世界: 当这种研究的精确性一超过某种限度时,几何学由于其近似地反映现实的本质,就失去了作用。 为了使它重新成为有用的,我们必须依据新的实验数据使它成为更精确的,我们必须回过来捡起在抽象 过程中弃之于途的那些东西。 然而在我们建立几何学时,物质现实,究竟有哪些较为显眼的方面,被抛弃掉了呢?这首先就是物质在 一定的时间内所进行的运动。很自然地,为了在几何学里避免过分的抽象,使它接近于物质现实,我们应该 重新考虑物质运动的过程,而这就说明,应该把几何学放在与力学结合成的有机整体中来讨论。”纯粹的” 几何学消失了。 以上所说的种种不只属于理论上的探讨,20 世纪内科学的历史发展正就是沿着这条道路前进的。狭义 相对论(1905)把空间和时间的延伸性结合成一个不可分割的整体,而广义相对论(1916)更把几何学和关 于物质的分布和运动的普遍学说统一在一个学科之中。因此,从到现在为止我们关于几何学所说的那种观点 看来,它是物理学的一部分,因而就应该与在实验基础上的物理学一起生长和发展。 然而在几何学里还有别的、数学的方面,那是我们直到现在为止有意地置之不理的。而这方面目前对于 我们是最重要的,因为它正是本书所要讲述的。
为什么使用WKHtmlToPdf:
https://blog.csdn.net/qq_34190023/article/details/82999702
这篇文章有详细的介绍。
技术特点:
Wkhtmltopdf可直接把浏览器中浏览的网页转换成一个pdf,他是一个把html页面转换成pdf的软件(需要安装在服务器上)。使用时可通过java代码调用cmd指令完成网页转换为pdf的功能。
优点:
支持中文、图片、CSS等
缺点:
有时对于html文件的转化可能比较慢,对于url的转化速度较快。存在失真情况。
安装:
一、下载
打开官网:https://github.com/wkhtmltopdf/packaging/releases/0.12.1.4-2/
根据Comments的提示,选择适合自己的版本。
二、Linux下的使用
无需任何安装,现在可以开始直接使用了。
1、先将刚才下载的包解压:tar -xvf wkhtmltox-0.12.4_linux-generic-amd64.tar.xz
2、然后运行/data/wkhtmltox/bin/wkhtmltopdf www.baidu.com pdf.pdf
(前面的目录/data,大家根据自己的解压路径定)
运行成功!
3、将wkhtmltopdf拷入执行目录下:cp /data/wkhtmltox/bin/wkhtmltopdf /usr/local/bin/wkhtmltopdf
这样就不用敲一长串路径了,比如:wkhtmltopdf www.baidu.com pdf.pdf
提示:这个工具包中有两个组件,还有一个wkhtmltoimage可以把HTML转成IMG。
wkhtmltoimage下载:
wget https://github.com/wkhtmltopdf/wkhtmltopdf/releases/download/0.12.4/wkhtmltox-0.12.4_linux-generic-amd64.tar.xz
三、解决中文乱码问题
1、创建字库目录,把相应字库文件复制到该目录
[root@updev1 ~]# cd /usr/share/fonts
[root@updev1 fonts]# mkdir chinese
把 将 windows下的字体,例如 c:\WINDOWS\Fonts\simsun.ttf 文件复制到该目录
2、生成字库索引信息
[root@updev1 fonts]# cd chinese
[root@updev1 chinese]# mkfontscale
[root@updev1 chinese]# mkfontdir
[root@updev1 chinese]# ll
total 10264
-rw-r–r-- 1 root root 189 Sep 6 17:46 fonts.
BatchNorm怎样解决训练和推理时batch size 不同的问题? BatchNorm是在batch维度上计算每个相同通道上的均值和方差,通常情况下,训练阶段的batchsize较大,而推理时batchsize基本为1。这样的话,就会导致训练和推理阶段得到不同的标准化,均值和方差时靠每一个mini-batch的统计得到的,因为推理时只有一个样本,在只有1个向量的数据组上进行标准化后,成了一个全0向量,导致模型出现BUG。为了解决这个问题,不改变训练时的BatchNorm计算方式,仅仅改变推理时计算均值和方差方法。
做法就是用训练集来估计总体均值 μ \mu μ和总体标准差 σ \sigma σ。主要有两种方法:简单平均法和移动指数平均
简单平均法
把每个mini-batch的均值和方差都保存下来,然后训练完了求均值的均值,方差的均值即可。 移动指数平均(Exponential Moving Average)
本文仅以 μ \mu μ的计算为例:
μ t o t a l = d e c a y ∗ μ t o t a l + ( 1 − d e c a y ) ∗ μ \mu_{total}=decay*\mu_{total}+(1-decay)*\mu μtotal=decay∗μtotal+(1−decay)∗μ
其中decay是衰减系数。即总均值 μ t o t a l \mu_{total} μtotal是前一个mini-batch统计的总均值和本次mini-batch的 μ \mu μ加权求和。至于衰减率 decay在区间[0,1]之间,decay越接近1,结果 μ t o t a l \mu_{total} μtotal越稳定,越受较远的大范围的样本影响;decay越接近0,结果 μ t o t a l \mu_{total} μtotal越波动,越受较近的小范围的样本影响。 事实上,简单平均可能更好,简单平均本质上是平均权重,但是简单平均需要保存所有BN层在所有mini-batch上的均值向量和方差向量,如果训练数据量很大,会有较可观的存储代价。移动指数平均在实际的框架中更常见(例如tensorflow),可能的好处是EMA不需要存储每一个mini-batch的值,永远只保存着三个值:总统计值、本batch的统计值,decay系数。