Git
-
git是一个分布式的版本控制软件,版本控制最早期是文件的复制粘贴、下一个阶段是集中管理、现在是分布式管理。
-
集中管理是将文件存储到一个地方,优点是解决了共同开发,缺点也很明显就是如果存储的地方出现问题就无法使用了。
-
分布式管理就很好了在网络中的每个点都存储一遍,优点是哪个节点出现问题都不影响其他节点。
-
安装:去https://git-scm.com/下载后,点下一步即可。
1.基本使用
-
右键点击bash here,版本查看
git --version
。 -
进入要管理的文件夹打开Bash Here后,输入
git init
作用是初始化,初始化后需要查看一下文件夹中的文件使用git status
。 -
查看后你会发现文件是红色的,红色代表未在工作区,我们需要将其添加到缓存区使用
git add "FileName"
或全部添加git add .
,文件修改后并不在管理范围之内,所以需要再次添加并生成新的版本。 -
我们第一次使用git去生成版本时会出现一个提示,说是要你填写Email and Name,填写这两个是为了让git记住你。
git config --global user.email "[email protected]" git config --global user.name "Your Name"
-
添加完之后我们需要生成版本使用
git commit -m "VersionName"
,生成版本后我们肯定要查看的所以我们使用git log
查看。 -
版本生成后你就会发现,如果有一天需要将一个功能取消,你不可能一行一行去删,这里只能用到回滚了。
git add "FileName" # 添加到缓存区 git commit "versionName" # 添加到版本库 git reset --soft "VersionNum" # 退回到缓存区 git reset head "FileName" # 退回到工作区(exit) git check out "FileName" # exit退回到start git reset --mix "VersionName" # 版本库退回到工作区exit git reset --hard "VersionName" # 版本库退回到工作区start(想退回到上一个版本,就查看历史版本后,使用这条命令) git reflog # 查看历史版本
-
你有没有想过版本库的存储方式是什么,如果我有两个功能要开发你需要找两个人开发,而版本库需要使用分支来存储,分支的好处在于两个人的开发并不会互相影响。有多个分支要合并时,如果两个分支修改同一行代码时,会出现提示需要手动删除不需要的合并部分。(合并时先转到主分支)
git branch # 查看分支 git branch "BranchName" # 创建分支 git checkout "BranchName" # 切换分支 git merge "BranchName" # 合并分支 git branch -d "BranchName" # 删除分支
-
在公司我们开发需要至少创建两个分支,一个是正式分支、另一个是开发分支,只有开发分支稳定后再去合并到正式分支中。
2.远程仓库(GitHub)
-
远程仓库GitHub存储你写的代码前需要创建账户和仓库,创建后拿到仓库RUL后到自己的电脑上使用以下命令即可。
git remote add "origin" "URL" # 给仓库创建别名 git push -u "origin" "master" # 推送分支到仓库 git clone "URL" # 克隆远程的仓库并帮你给仓库起别名为origin,创建别名只需要一次即可。 git pull "origin" "dev" # 更新本地代码
-
在
git pull "origin" "dev"
等于git fetch "origin" "dev"
(是将github上的代码拉到版本库的)+git merge origin/dev
(是将拉到版本库的代码放到工作区)。 -
在工作中代码需要合并的,这里我们在合并有三种应用场景。
-
在工作中版本太多后,给老板给时不可能交给多个版本,我们只能将版本合并起来交给老板。
git rebase -i "VersionNum" # 将该码以上的全部合并 git rebase -i HEAD~3 # 合并当前版本下3个,版本可以随意。 # 注意: 修改前面为s,s代表将s代表的合并到pick版本上。 版本合并时会出现描述,你需要写一下描述。
-
在两个分支便携时会出现,分支合并并不会直接合并只会让它新生产一个版本合并的,而你想合并成一条时可以如下操作。
git checkout dev git rebase master git chekcout master git merge dev git log --graph --pretty-format:"%h %s" # 简化显示
-
在GitHub上的代码是最新的,而在你的电脑上的并不是,你需要拉下来但是拉下来会新创建一个版本,我们可以使用一下代码将其合并。
git fetch "origin" "dev" git checkout "dev" git rebase "master" git rebase --continue # 注意:修改冲突带代码,后并添加到暂存区后继续执行下去。
-
-
我们在公司开发时,git的使用应该是一个主分支,一个开发分支,在开发分支下又有多个功能分支,功能分支完成开发后合并到开发分支,开发分支需要先合并到测试分支,测试完之后再合并到主分支即可。
3.其他
3.1 快速解决冲突
-
快速解决冲突我们需要使用的一个软件,“beyond compare”用来快速解决冲突代码。
-
我们需要在git中配置该文件后,才可以使用。
git config --local merge.tool bc3 # 起名字为bc3 git config --local mergetool.path "PATH" # 指定软件路径 git config --local mergetool.keepBackup false # 解决冲突后并不保留,备份
-
剩下的就是使用了,用
git mergetool
启动beyond compare。
3.2 git配置文件
-
git有三个配置文件,项目、所有项目和系统三种,使用不同的命令配置。
-
配置文件的位置。
# 项目配置文件"project/.git/config" git config --local # 全局配置文件"~/.gitconfig" git config --global # 系统配置文件"/etc/.gitconfig" git config --system
3.3 GitHub免密登录
-
URL中免密,是使用将用户名密码拼接在连接中并配置在,git配置文件中实现的。
git remote add origin https://UserName:[email protected]/...
-
SSH实现免密,使用公钥和私钥将其实现免密,是将公钥放到GitHub的settings中配置后即可使用。
# 生成公钥和私钥(默认放在~/.ssh目录下的,id_rsa.pub公钥、id_rsa私钥) ssh-keygen git remote add origin [email protected]/...
3.4 git忽略文件
-
git想要忽略文件就需要创建一个文件
gitignore
并在里面写如需要忽略的文件。(*.h:应用.h结尾文件、!a.h:不应用这个文件、files/:忽略该文件夹下的所有文件、a.py[a|b]:忽略a.pya和a.pyb的文件)。
rabbmitMQ
-
消息队列分为两种一种是ssh只需要在服务以上安装下面的机器都可以使用,另一种是agent下面的每个机子都需要安装。但是agent的效率高,速度快,服务器只需要下达命令,它们就会去队列中自己去取,执行完后自动将数据放到消息队列。
-
公司在什么情况下才会用到消息队列?只有在任务处理不过来的时候才会用到,避免程序堵塞。
1.基本配置
-
安装
# 服务器端 # 安装配置epel源 $ rpm -ivh http://dl.fedoraproject.org/pub/epel/6/i386/epel-release-6-8.noarch.rpm # 安装erlang $ yum -y install erlang # 安装RabbitMQ $ yum -y install rabbitmq-server # 客户端 pip3 install pika
-
启动
service rabbitmq-server start/stop
-
设置用户密码
sudo rabbitmqctl add_user wupeiqi 1234 # 设置用户为administrator sudo rabbitmqctl set_user_tags wupeiqi administrator # 设置权限 sudo rabbitmqctl set_permissions -p "/" root ".*" ".*" ".*"
2.生产者和消费者
-
生产者
import pika # 无密码 # connection = pika.BlockingConnection(pika.ConnectionParameters("localhost")) # 创建连接 # 有密码 credentials = pika.PlainCrredentials("root","123") connection = pika.BlockingConnection(pika.ConnectionParameters("localhost",credentials=credentials))# 创建连接 channel = connection.channel() channel.queue_declare(queue="hello") # 声明一个队列 channel.basic_publish(exchange="", routing_key="hello", # 队列名 body="asdfasdf") # 数据 connection.close() # 关闭连接
-
消费者
import pika # 有密码 credentials = pika.PlainCrredentials("root","123") connection = pika.BlockingConnection(pika.ConnectionParameters("localhost",credentials=credentials))# 创建连接 channel = connection.channel() channel.queue_declare(queue="hello") # 声明一个队列 def callback(ch, method, properties, body): print("消费者接收到任务:%r" % body) channel.basic_consune(callback, queue="hello", no_ack=True) # 接收后调用函数 channel.start_consuning() # 开始接收
3.ack回复和持久化
-
生产者
import pika # 无密码 # connection = pika.BlockingConnection(pika.ConnectionParameters("localhost")) # 创建连接 # 有密码 credentials = pika.PlainCrredentials("root","123") connection = pika.BlockingConnection(pika.ConnectionParameters("localhost",credentials=credentials))# 创建连接 channel = connection.channel() channel.queue_declare(queue="hello", durable=True) # 声明一个队列,协商durable=True后就支持持久化了,不过需要重新创建一个队列才可以使用 channel.basic_publish(exchange="", routing_key="hello", # 队列名 body="asdfasdf", # 数据 properties=pika.BasicProperties( delivery_mode = 2, # 这里也需要配置才可以持久化 )) connection.close() # 关闭连接
-
消费者
import pika # 有密码 credentials = pika.PlainCrredentials("root","123") connection = pika.BlockingConnection(pika.ConnectionParameters("localhost",credentials=credentials))# 创建连接 channel = connection.channel() channel.queue_declare(queue="hello") # 声明一个队列 def callback(ch, method, properties, body): print("消费者接收到任务:%r" % body) ch.basic_ack(delivery_tag=method.delivery_tag) # 回复服务器可以删除值了 channel.basic_qos(prefetch_count=1) # 在rabbmitMQ中是均匀分配的,但是有一种情况是一个节点执行的慢,这个节点肯定不能使用均匀分配了,只要加上这句就可以实现空闲分配了。 channel.basic_consune(callback, queue="hello", no_ack=False) # 接收后调用函数,你在不适用ack是消费者会直接将数据取走,当你启用ack后你去取数据时会先复制一份你先用,当你回复后再将数据删除。 channel.start_consuning() # 开始接收
4.durable
-
生产者
import pika # 有密码 credentials = pika.PlainCrredentials("root","123") connection = pika.BlockingConnection(pika.ConnectionParameters("localhost",credentials=credentials))# 创建连接 channel = connection.channel() channel.exchange_declare(exchange="m1", exchange_type="fanout") # 防止生产者先运行,这样可以实现一个生产者发送,多个消费者接收的情况。 channel.basic_publish(exchange="m1", routing_key="sb", # 使用了exchange后对列名就变成了关键名了,被定义的人才可以接收到消息。 body="asdfasdf", # 数据 ) connection.close() # 关闭连接
-
消费者
import pika # 有密码 credentials = pika.PlainCrredentials("root","123") connection = pika.BlockingConnection(pika.ConnectionParameters("localhost",credentials=credentials))# 创建连接 channel = connection.channel() channel.exchange_declare(exchange="m1", exchange_type="fanout") # exchange是消费者的名称,exchange_type消费者的工作模式 # 用于生成随机队列名称 result = channel.queue_declare(exclusive=True) queue_name = result.method.queue # 让exchange和queque进行绑定,这里的列表名是关健名了,只有使用了的人才可以收到制定的消息。 channel.queue_bind(exchange="m1", queue=queue_name, routing_key="sb.*") # 当你不知道发送的人是谁,可以使用模糊查找来发送*代表一个单词,#号代表多个单词。 def callback(ch, method, properties, body): print(method.routing_key) # 显示发过来的key print("消费者接收到任务:%r" % body) channel.basic_consune(callback, queue=queue_name, no_ack=True) channel.start_consuning() # 开始接收
垃圾回收和内存管理
-
引用计数器为主,标记清除和分代回收为辅。
引用计数器
环形双向链表 Refchain
-
在python程序中创建的任何对象都会放在refchain链表中。
-
每个对象会常见基本的资格对象(上一个对象、下一个对象、类型、引用个数),每个类型中还有不同的对象。如:字典由itme。
-
在c源码中如何体现每个对象中都有的相同的值:PyObject结构体(4个值)。
-
由多个元素组成的对象:PyObject结构体+ob_size。
-
c中编写的数据类型
#define PyObject_HEAD PyObject ob_base; #define PyObject_VAR_HEAD PyVarObject ob_base; // 宏定义,包含上一个、下一,用于构造双向链表用。 #define _PyObject_HEAD_EXTRA struct _object *_ob_next; struct _object *_ob_prev; typedef struct _object { _PyObject_HEAD_EXTRA // 用于构造双向链表 Py_ssize_t ob_refcnt; // 引用计数器 struct _typeobject *ob_type // 数据类型 } PyObject; typedef struct { PyObject ob_base; Py_ssize_t ob_size; }PyVarObject; // float typedef struct { PyObject_HEAD double ob_fval; } PyFloatObject; // int struct _longobject { PyObject_VAR_HEAD digit ob_digit[1]; }; typedef struct _longobject PyLongObject; // list typedef struct { PyObject_VAR_HEAD PyOBject **ob_item; Py_ssize_t allocated; } // tuple typedef struct { PyObject_VAR_HEAD PyObject *ob_item[1]; } PyTupleObject; // dict typedef struct { PyObject_HEAD Py_ssize_t ma_used; PyDictKeysObject *ma_keys; PyObject **ma_values; } PyDictObject;
-
引用计数器是你常见了一个对象后,被其他变量所应用(并不是复制),引用会被增加或减少del删除引用后就会减少。
标记清除
-
在对象引用中我们会发现,列表在取出所有的应用后,依然存在于内存之中。这是应为计数器循环引用的问题。
-
在python的底层再维护一个链表,链表中专门放哪些可能存在循环引用的对象。
-
在python内部某种情况下触发,回去扫描可能存在循环引用的链表中的每个元素,检查是否有循环引用,如果有则让双方的引用计数器-1;如果是0则垃圾回收。
分代回收
-
将可能存在循环引用的对象维护成3个链表:
-
0代:0代中对象个数达到700个扫描一次。
-
1代:0代扫描10次,则1代扫描一次。
-
2代:1代扫描10次,则2代扫描一次。
-
缓存机制
-
为了避免重复创建和销毁一些常见对象,所以出现了池。
-
池中会创建常用的一些对象,当你调用这个对象是,他们的内存地址是指定的。
-
当一个对象的引用计数器为0时,按理来说应该回收,内部不会直接回收,而是将对象添加到free_list列表中当缓存。以后再去创建对象时,不再重新开辟内存,而是直接使用free_list中的对象。free_list(80),销毁的内存地址和创建的内存地址是一样的。
支付宝案例
标签:git,pika,queue,connection,PythonOther,credentials,channel From: https://www.cnblogs.com/InvincibleGrass/p/17740885.html