<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>其它 &#8211; 有意与无意之间</title>
	<atom:link href="https://zhangxihai.cn/archives/category/other/feed" rel="self" type="application/rss+xml" />
	<link>https://zhangxihai.cn</link>
	<description>千淘万漉虽辛苦 吹尽狂沙始到金 - 生命不息 编程不止</description>
	<lastBuildDate>Fri, 01 Sep 2023 03:00:17 +0000</lastBuildDate>
	<language>zh-CN</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.0.11</generator>
	<item>
		<title>Debian11启用BBR加速</title>
		<link>https://zhangxihai.cn/archives/230</link>
					<comments>https://zhangxihai.cn/archives/230#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Thu, 01 Sep 2022 02:56:16 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=230</guid>

					<description><![CDATA[1 修改系统配置 echo &#34;net.core.default_qdisc=fq&#34; &#62;&#62; /etc/sysctl.conf &#38;&#38; echo &#34;net.ipv4.tcp_congestion_control=bbr&#34; &#62;&#62; /etc/sysctl.conf 2 启用配置 sysct...]]></description>
										<content:encoded><![CDATA[<h5>1 修改系统配置</h5>
<pre><code>echo &quot;net.core.default_qdisc=fq&quot; &gt;&gt; /etc/sysctl.conf &amp;&amp; echo &quot;net.ipv4.tcp_congestion_control=bbr&quot; &gt;&gt; /etc/sysctl.conf</code></pre>
<h5>2 启用配置</h5>
<pre><code>sysctl -p</code></pre>
<h5>3 查看内核是否生效</h5>
<pre><code>sysctl net.ipv4.tcp_available_congestion_control</code></pre>
<p>显示<code>net.ipv4.tcp_available_congestion_control = reno cubic bbr</code>为已生效</p>
<h5>4 查看BBR是否启动</h5>
<pre><code>lsmod | grep bbr</code></pre>
<p>显示<code>tcp_bbr                20480  1</code>即为已生效</p>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/230/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>尝鲜.NET6 Preview4， 然后悲剧了</title>
		<link>https://zhangxihai.cn/archives/163</link>
					<comments>https://zhangxihai.cn/archives/163#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Fri, 28 May 2021 01:10:49 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<category><![CDATA[dotnet]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=163</guid>

					<description><![CDATA[早上安装.NET6 Preview4尝鲜，然后悲剧了。VS任何.NET项目都打不开，因为.NET6 Preview4要求比如使用wokerloafer负载分析器，且不能在环境变量中设置不需要。而VS FOR MAC才到8.9， 根本没有解决这个。 WIN中VS版本过了preview 16.3就解决这个问题了。 看来得用一段时间vs code了。]]></description>
										<content:encoded><![CDATA[<p>早上安装.NET6 Preview4尝鲜，然后悲剧了。VS任何.NET项目都打不开，因为.NET6 Preview4要求比如使用wokerloafer负载分析器，且不能在环境变量中设置不需要。而VS FOR MAC才到8.9， 根本没有解决这个。 WIN中VS版本过了preview 16.3就解决这个问题了。 看来得用一段时间vs code了。</p>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/163/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>使用nginx + minio + imageproxy 搭建私有图床</title>
		<link>https://zhangxihai.cn/archives/100</link>
					<comments>https://zhangxihai.cn/archives/100#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Wed, 06 Jan 2021 05:07:05 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=100</guid>

					<description><![CDATA[MinIO 是一个基于Apache License v2.0开源协议的对象存储服务。它兼容亚马逊S3云存储服务接口，非常适合于存储大容量非结构化的数据，例如图片、视频、日志文件、备份数据和容器/虚拟机镜像等，而一个对象文件可以是任意大小，从几kb到最大5T不等。 图床的基础是Minio, 但minio并不提供图片缩略和裁剪功能，所以还需要用到Imagepro...]]></description>
										<content:encoded><![CDATA[<p>MinIO 是一个基于Apache License v2.0开源协议的对象存储服务。它兼容亚马逊S3云存储服务接口，非常适合于存储大容量非结构化的数据，例如图片、视频、日志文件、备份数据和容器/虚拟机镜像等，而一个对象文件可以是任意大小，从几kb到最大5T不等。</p>
<p>图床的基础是Minio, 但minio并不提供图片缩略和裁剪功能，所以还需要用到Imageproxy和Nginx。</p>
<p>基于Docker安装更方便，但是不是很想用Docker，所以采用了编译安装。</p>
<h3>编译安装nginx</h3>
<p>安装第三方依赖:</p>
<pre><code class="language-shell">yum -y install gcc gcc-c++ automake pcre pcre-devel zlib zlib-devel openssl openssl-devel</code></pre>
<p>创建nginx用户:</p>
<pre><code class="language-shell">groupadd nginx
useradd nginx -g nginx -s /sbin/nologin -M</code></pre>
<p>从官方下载nginx源码包并解压：</p>
<pre><code class="language-shell">wget https://nginx.org/download/nginx-1.17.0.tar.gz
tar -zxvf nginx-1.17.0.tar.gz
cd nginx-1.17.0</code></pre>
<p>配置nginx</p>
<pre><code class="language-shell">./configure --prefix=/usr/local/nginx --conf-path=/usr/local/nginx/conf/nginx.conf --error-log-path=/var/log/nginx/error.log --modules-path=/usr/lib64/nginx/modules --http-log-path=/var/log/nginx/access.log --pid-path=/var/run/nginx.pid --lock-path=/var/run/nginx.lock --user=nginx --group=nginx --with-http_ssl_module --with-http_v2_module --with-http_dav_module --with-http_stub_status_module --with-threads --with-file-aio --with-http_gzip_static_module</code></pre>
<p>安装</p>
<pre><code class="language-shell">make &amp;&amp; make install</code></pre>
<p>配置管理，这里是centos7:</p>
<pre><code class="language-shell">vim /usr/lib/systemd/system/nginx.service</code></pre>
<p>输入以下</p>
<pre><code class="language-shell">[Unit]
Description=The NGINX HTTP and reverse proxy server
After=syslog.target network.target remote-fs.target nss-lookup.target

[Service]
Type=forking
PIDFile=/var/run/nginx.pid
ExecStartPre=/usr/local/nginx/sbin/nginx -t
ExecStart=/usr/local/nginx/sbin/nginx
ExecReload=/usr/local/nginx/sbin/nginx -s reload
ExecStop=/bin/kill -s QUIT $MAINPID
PrivateTmp=true

[Install]
WantedBy=multi-user.target</code></pre>
<p>启用nginx服务并设置为开机启动：</p>
<pre><code class="language-shell">systemctl daemon-reload
systemctl start nginx.service
systemctl enable nginx.service</code></pre>
<h3>安装minio</h3>
<p>直接下载minio的二进制包就可以直接使用：</p>
<pre><code class="language-shell">cd /usr/local/bin
wget https://dl.min.io/server/minio/release/linux-amd64/minio
chmod +x minio</code></pre>
<p>为minio创建本地存储位置:</p>
<pre><code class="language-shell">mkdir -p /storage</code></pre>
<p>编辑minio服务器配置，其中9159是服务端口，MINIO_ACCESS_KEY是访问秘钥，MINIO_SECRET_KEY是加密秘钥：</p>
<pre><code class="language-shell">cat &lt;&lt;EOT &gt;&gt; /etc/default/minio
\# miinio存储名
MINIO_REGION_NAME=xman
\# minio存储卷.
MINIO_VOLUMES=/storage
\# 自定义MinIo管理.
MINIO_OPTS=&quot;--address :9159&quot;
\# 服务器Access Key.
MINIO_ACCESS_KEY=admin
\# 服务器Secret key.
MINIO_SECRET_KEY=123456789
EOT</code></pre>
<p>创建minio管理：</p>
<pre><code class="language-shell">cd /etc/systemd/system/
curl -O https://raw.githubusercontent.com/minio/minio-service/master/linux-systemd/distributed/minio.service</code></pre>
<p>注意修改其中的用户及群组</p>
<p>启用minio服务并设置开机启动</p>
<pre><code class="language-shell">systemctl daemon-reload
systemctl start minio.service
systemctl enable minio.service</code></pre>
<h3>安装imageproxy</h3>
<h4>安装go</h4>
<p>imageproxy是go编写的一款图片缩放裁剪代理程序，所以要先安装golang环境：</p>
<p>下载go并解压</p>
<pre><code class="language-shell">wget https://golang.google.cn/dl/go1.15.6.linux-amd64.tar.gz
tar -zxvf go1.15.6.linux-amd64.tar.gz</code></pre>
<p>将go加入系统环境：</p>
<pre><code class="language-shell">vim /etc/profile</code></pre>
<p>在文件尾部输入:</p>
<pre><code class="language-shell">#golang env config
export GO111MODULE=on
export GOROOT=/usr/local/go 
export GOPATH=/home/gopath
export PATH=$PATH:$GOROOT/bin:$GOPATH/bin</code></pre>
<p>执行：</p>
<pre><code class="language-shell">source /etc/profile</code></pre>
<p>立即启用go</p>
<p><strong>安装Aws cli</strong><br />
imageproxy需要 aws s3的支持，所以需要安装 aws cli</p>
<p>使用pip安装最新版本</p>
<pre><code class="language-shell">yum -y install epel-release
yum -y install python-pip
pip install awscli</code></pre>
<p>安装完成需要进行配置</p>
<pre><code class="language-shell">aws configure</code></pre>
<p>按照提示输入</p>
<pre><code class="language-shell">AWS Access Key ID [None]: Q3AM3UQ867SPQQA43P2F  # 输入刚才设置的MINIO_ACCESS_KEY
AWS Secret Access Key [None]: zuf+tfteSlswRu7BJ86wekitnifILbZam1KYY3TG # 输入刚才设置的MINIO_SECRET_KEY
Default region name [None]: us-east-1  #输入这个就可以
Default output format [None]: 回车默认就介意
aws configure set default.s3.signature_version s3v4</code></pre>
<p>配置成功后，使用aws创建存储桶以验证配置是否正确，也未下一步做准备：<br />
创建存储桶:</p>
<pre><code class="language-shell">aws --endpoint-url http://127.0.0.1:9159 s3 mb s3:/imageproxy</code></pre>
<p><strong>安装imageproxy</strong><br />
直接通过go安装:</p>
<pre><code class="language-shell">go get willnorris.com/go/imageproxy/cmd/imageproxy</code></pre>
<p>安装完成后配置管理</p>
<pre><code class="language-shell">vim /etc/systemd/system/imageproxy.service</code></pre>
<p>输入以下内容：</p>
<pre><code>[Unit]
Description=ImageProxy
Documentation=https://github.com/willnorris/imageproxy
Wants=network-online.target
After=network-online.target
AssertFileIsExecutable=/usr/local/bin/minio

[Service]
WorkingDirectory=/usr/local

User=root
Group=root

EnvironmentFile=-/etc/default/minio
ExecStartPre=/bin/bash -c &quot;if [ -z \&quot;${MINIO_ACCESS_KEY}\&quot; ]; then echo \&quot;Variable MINIO_ACCESS_KEY not set in /etc/default/minio\&quot;; exit 1; fi&quot;
ExecStartPre=/bin/bash -c &quot;if [ -z \&quot;${MINIO_SECRET_KEY}\&quot; ]; then echo \&quot;Variable MINIO_SECRET_KEY not set in /etc/default/minio\&quot;; exit 1; fi&quot;

ExecStart=/home/gopath/imageproxy  -cache &quot;s3://us-east-1/imageproxy/thumbnail?endpoint=127.0.0.1:9159&amp;disableSSL=1&amp;s3ForcePathStyle=1&quot; -addr 0.0.0.0:8001

# Let systemd restart this service always
Restart=always

# Specifies the maximum file descriptor number that can be opened by this process
LimitNOFILE=65536

# Disable timeout logic and wait until process is stopped
TimeoutStopSec=infinity
SendSIGKILL=no

[Install]
WantedBy=multi-user.target

# Built for ${project.name}-${project.version} (${project.name})</code></pre>
<p>启用imageproxy并设置开机启动：</p>
<pre><code class="language-shell">systemctl daemon-reload
systemctl start imageproxy.service
systemctl enable imageproxy.service</code></pre>
<h3>配置nginx反代</h3>
<p>imageproxy和minio都提供对外的web服务，但要将二者结合就最好使用nginx反代。</p>
<p>服务器配置如下</p>
<pre><code class="language-shell">server {
    listen 80;

    server_name youdomian.com;

    location ~ /thumb/ {
        rewrite ^/(?i)thumb(.*) $1 break;
        add_header Access-Control-Allow-Origin *;
        add_header Access-Control-Allow-Methods &quot;GET, POST, PUT, DELETE, OPTIONS&quot;;
        proxy_set_header Host $proxy_host;
        proxy_set_header X-Forwarded-For  $proxy_add_x_forwarded_for;
        proxy_pass http://127.0.0.1:8001;
    }

    location ~ /ImageView/ {
        rewrite ^(.*)/(?i)ImageView/(.*) /$2/http://127.0.0.1:9159$1 break;
        add_header Access-Control-Allow-Origin *;
        add_header Access-Control-Allow-Methods &quot;GET, POST, PUT, DELETE, OPTIONS&quot;;
        proxy_set_header Host $proxy_host;
        proxy_set_header X-Forwarded-For  $proxy_add_x_forwarded_for;
        proxy_pass http://127.0.0.1:8001;
    }

    location / {
        proxy_set_header Host $http_host;
        proxy_pass http://127.0.0.1:9159;
    }
}</code></pre>
<h3>使用</h3>
<p>访问<br />
<a href="http://youdomain.com/test/2.jpeg">http://youdomain.com/test/2.jpeg</a><br />
这是直接反代到minio的</p>
<p>访问<br />
<a href="http://youdomian.com/test/2.jpeg/ImageView/100">http://youdomian.com/test/2.jpeg/ImageView/100</a><br />
这是先反代到imageproxy， 再缩略缓存至minio的方式</p>
<p>访问<br />
<a href="http://youdomian.com/thumb/100/http://youdomain.com/test/2.jpeg">http://youdomian.com/thumb/100/http://youdomain.com/test/2.jpeg</a><br />
这是先反代到imageproxy， 再缩略缓存至minio的方式， 和上面的方式的区别在于这是imageproxy原反代方式， 而且可以反代非minio外部站点的url</p>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/100/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Go开源项目收集整理</title>
		<link>https://zhangxihai.cn/archives/98</link>
					<comments>https://zhangxihai.cn/archives/98#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Sun, 03 Jan 2021 14:26:08 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<category><![CDATA[golang]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=98</guid>

					<description><![CDATA[目录 存储服务 Key-Value键值对存储 文件系统 数据库 Database Drivers 存储 minio - Minio是一个与Amazon S3接口兼容的开源对象存储服务器。 rclone - &#34;云存储异步存储&#34; - Google Drive, Amazon Drive, S3, Dropbox, Backblaze B2, ...]]></description>
										<content:encoded><![CDATA[<h3>目录</h3>
<ul>
<li><a href="#存储服务">存储服务</a></li>
<li><a href="#Key-Value键值对存储">Key-Value键值对存储</a></li>
<li><a href="#文件系统">文件系统</a></li>
<li><a href="#数据库">数据库</a></li>
<li><a href="#database-drivers">Database Drivers</a></li>
</ul>
<h2>存储</h2>
<ul>
<li><a href="https://github.com/minio/minio">minio</a> - Minio是一个与Amazon S3接口兼容的开源对象存储服务器。 </li>
<li><a href="https://github.com/ncw/rclone">rclone</a> - &quot;云存储异步存储&quot; - Google Drive, Amazon Drive, S3, Dropbox, Backblaze B2, One Drive, Swift, Hubic, Cloudfile…</li>
<li><a href="https://github.com/perkeep/perkeep">perkeep</a> - Perkeep是一款个人存储系统：存储、同步、共享、建模和备份个人内容。 </li>
<li><a href="https://github.com/s3git/s3git">s3git</a> - 云存储Git,可用于数据的分布式版本控制。</li>
<li><a href="https://github.com/storj/storj">storj</a> - 分散的云对象存储，价格合理、易于使用、私有且安全。 </li>
<li><a href="https://github.com/rook/rook">rook</a> - 开放、云本机和通用分布式存储。</li>
<li><a href="https://github.com/rancher/longhorn">longhorn</a> - Longhorn是一个通过容器交付的开源持久块存储服务器。</li>
</ul>
<h2>Key-Value键值对存储</h2>
<ul>
<li><a href="https://github.com/prologic/bitcask">Bitcask</a> - Bitcask是一个可嵌入的、持久的、快速的键值（KV）数据库，使用纯Go编写，具有可预测的读/写性能、低延迟和高吞吐量，这得益于Bitcask磁盘布局（LSM+WAL）。</li>
<li><a href="https://github.com/prologic/bitraft">Bitraft</a> - Bitraft是一种基于raft的分布式密钥/值存储，具有与Redis兼容的协议。 它使用了 <a href="https://github.com/prologic/bitcask">Bitcask</a> 实现高性能/吞吐量和低延迟。</li>
<li><a href="https://github.com/dgraph-io/badger">BadgerDB</a> - BadgerDB是一个可嵌入的、持久的、简单快速的键值（KV）数据库，用纯Go编写。它的目的是成为RocksDB等基于Go的键值存储的性能替代品。</li>
<li><a href="https://github.com/dcoker/biscuit">biscuit</a> - Biscuit是一个多区域HA键值存储库，用于存储AWS基础设施机密。</li>
<li><a href="https://github.com/hashicorp/consul">consul</a> - 用于服务发现和配置的分布式一致复制键值存储。</li>
<li><a href="https://github.com/peterbourgon/diskv">diskv</a> - 磁盘备份的键值存储。</li>
<li><a href="https://github.com/coreos/etcd">etcd</a> - 分布式系统中最关键数据的分布式可靠键值存储。</li>
<li><a href="https://github.com/patrickmn/go-cache">go-cache</a> - 记忆中的记忆键：值存储/缓存（类似于Memcached）library for Go，适合单机应用。</li>
<li><a href="https://github.com/xujiajun/nutsdb">nutsdb</a> - Nutsdb是一个用纯Go编写的简单、快速、可嵌入、持久的键/值存储。它支持完全可序列化的事务和许多数据结构，如列表、集合、排序集。</li>
</ul>
<h2>文件系统</h2>
<ul>
<li><a href="https://github.com/spf13/afero">afero</a> - GO编写的文件抽象系统。</li>
<li><a href="https://github.com/fsnotify/fsnotify">fsnotify</a> - Go的跨平台文件系统通知。</li>
<li><a href="https://github.com/GoogleCloudPlatform/gcsfuse">gcsfuse</a> - 与Google云存储交互的用户空间文件系统。</li>
<li><a href="https://github.com/git-lfs/git-lfs">git-lfs</a> - 用于控制大文件版本的Git扩展。</li>
<li><a href="https://github.com/coreos/go-systemd">go-systemd</a> - Go绑定到systemd套接字激活、日志、D-Bus和单元文件</li>
<li><a href="https://github.com/kahing/goofys">goofys</a> - 用Go编写的高性能POSIX-ish Amazon s3文件系统。</li>
<li><a href="https://github.com/geohot/minikeyvalue">minikeyvalue</a> - 1000行分布式键值存储。</li>
<li><a href="https://github.com/chrislusf/seaweedfs">seaweedfs</a> - SeaweedFS是一个简单且高度可扩展的分布式文件系统，适用于小文件。</li>
<li><a href="https://github.com/ovh/svfs">svfs</a> - 基于fuse的Openstack Swift虚拟文件系统。</li>
</ul>
<h2>数据库</h2>
<ul>
<li><a href="https://github.com/allegro/bigcache">BigCache</a> - 针对千兆字节数据的高效键/值缓存。</li>
<li><a href="https://github.com/boltdb/bolt">bolt</a> - 低级键/值数据库。</li>
<li><a href="https://github.com/tidwall/buntdb">buntdb</a> - 一个快速的、可嵌入的、内存中的键/值数据库，支持自定义索引和空间。</li>
<li><a href="https://github.com/muesli/cache2go">cache2go</a> - 支持时间超时自动失效的内存key/value的数据库。</li>
<li><a href="https://github.com/cockroachdb/cockroach">cockroach</a> - 可扩展的地理数据存储。</li>
<li><a href="https://github.com/codingsince1985/couchcache">couchcache</a> - 基于Couchbase服务器的Restful缓存微服务。</li>
<li><a href="https://github.com/CovenantSQL/CovenantSQL">CovenantSQL</a> - 具有区块链功能的SQL数据库。</li>
<li><a href="https://github.com/dgraph-io/dgraph">dgraph</a> - 可扩展、分布式、低延迟、高吞吐量的图形数据库。</li>
<li><a href="https://github.com/peterbourgon/diskv">diskv</a> - 自制的磁盘备份键值存储。</li>
<li><a href="https://github.com/krotik/eliasdb">eliasdb</a> - 无依赖关系的事务性图形数据库，带有RESTAPI、短语搜索和类似SQL的查询语言。</li>
<li><a href="https://github.com/emitter-io/emitter">emitter</a> - 可扩展、低延迟、分布式和安全的发布/子数据库，具有时间序列消息存储，适用于物联网、游戏、应用程序和实时web。</li>
<li><a href="https://github.com/couchbase/goforestdb">forestdb</a> - ForestDB的绑定。</li>
<li><a href="https://github.com/bluele/gcache">GCache</a> - 缓存库，支持过期缓存、LFU、LRU和ARC。</li>
<li><a href="https://github.com/melihmucuk/geocache">geocache</a> - 适用于基于地理位置的应用程序的内存缓存。</li>
<li><a href="https://github.com/pmylund/go-cache">go-cache</a> - 存储于内存的健/值对存储数据库(类似于memcached),适用于单机。</li>
<li><a href="https://github.com/syndtr/goleveldb">goleveldb</a> - [LevelDB] (<a href="https://github.com/google/leveldb">https://github.com/google/leveldb</a>) 健/值对数据库扩展。</li>
<li><a href="https://github.com/golang/groupcache">groupcache</a> -<br />
Groupcache是一个缓存和缓存填充库，在许多情况下可以替代memcached。</li>
<li><a href="https://github.com/influxdb/influxdb">influxdb</a> - 用于度量、事件和实时分析的可扩展数据存储。</li>
<li><a href="https://github.com/siddontang/ledisdb">ledisdb</a> - Ledisdb是一个基于LevelDB的高性能NoSQL类Redis。</li>
<li><a href="https://github.com/jmhodges/levigo">levigo</a> - Levigo是LevelDB的Go包装器。</li>
<li><a href="https://github.com/couchbase/moss">moss</a> - Moss是一个用100%Go编写的简单LSM键值存储引擎。</li>
<li><a href="https://github.com/attic-labs/noms">noms</a> - 版本化的、可分叉的、可同步的数据库。</li>
<li><a href="https://github.com/xujiajun/nutsdb">nutsdb</a> - Nutsdb是一个用纯Go编写的简单、快速、可嵌入、持久的键/值存储。它支持完全可序列化的事务和许多数据结构，如列表、集合、排序集。</li>
<li><a href="https://github.com/fern4lvarez/piladb">piladb</a> - 基于栈数据结构的轻量级RESTful数据库引擎。</li>
<li><a href="https://github.com/nuveo/prest">pREST</a> - 提供来自任何PostgreSQL数据库的restfulapi。</li>
<li><a href="https://github.com/prometheus/prometheus">prometheus</a> - 监控系统和时间序列数据库。</li>
<li><a href="https://github.com/rqlite/rqlite">rqlite</a> - 基于SQLite的轻量级分布式关系数据库。</li>
<li><a href="https://github.com/nanobox-io/golang-scribble">scribble</a> - 一个小的平面文件JSON存储。</li>
<li><a href="https://github.com/pingcap/tidb">tidb</a> - TiDB是一个分布式SQL数据库。灵感来自谷歌F1的设计。</li>
<li><a href="https://github.com/HouzuoGuo/tiedot">tiedot</a> - GO写的NOSQL数据库。</li>
<li><a href="https://github.com/tidwall/tile38">Tile38</a> - 具有空间索引和实时地理围栏的地理位置数据库。</li>
</ul>
<p><em>数据库迁移工具</em></p>
<ul>
<li><a href="https://github.com/GuiaBolso/darwin">darwin</a> - Go数据库模式演化库</li>
<li><a href="https://github.com/steinbacher/goose">goose</a> - 数据库迁移工具。您可以通过创建增量SQL或Go脚本来管理数据库的发展。</li>
<li><a href="https://github.com/go-gormigrate/gormigrate">gormigrate</a> - Gorm ORM的数据库架构迁移帮助程序。</li>
<li><a href="https://github.com/golang-migrate/migrate">migrate</a> - Database migration handling in Golang support MySQL, PostgreSQL, Cassandra, and SQLite.</li>
<li><a href="https://github.com/pravasan/pravasan">pravasan</a> - Simple Migration tool - currently for MySQL but planning to support soon for Postgres, SQLite, MongoDB, etc.,</li>
<li><a href="https://github.com/markbates/pop/tree/master/soda">soda</a> - Database migration, creation, ORM, etc... for MySQL, PostgreSQL, and SQLite.</li>
<li><a href="https://github.com/rubenv/sql-migrate">sql-migrate</a> - Database migration tool. Allows embedding migrations into the application using go-bindata.</li>
</ul>
<p><em>Database tools.</em></p>
<ul>
<li><a href="https://github.com/siddontang/go-mysql">go-mysql</a> - A go toolset to handle MySQL protocol and replication.</li>
<li><a href="https://github.com/siddontang/go-mysql-elasticsearch">go-mysql-elasticsearch</a> - Sync your MySQL data into Elasticsearch automatically.</li>
<li><a href="https://github.com/flike/kingshard">kingshard</a> - kingshard is a high performance proxy for MySQL powered by Golang.</li>
<li><a href="https://github.com/2tvenom/myreplication">myreplication</a> - MySql binary log replication listener. Support statement and row based replication.</li>
<li><a href="https://github.com/outbrain/orchestrator">orchestrator</a> - MySQL replication topology manager &amp; visualizer</li>
<li><a href="https://github.com/sosedoff/pgweb">pgweb</a> - A web-based PostgreSQL database browser</li>
<li><a href="https://github.com/youtube/vitess">vitess</a> - vitess provides servers and tools which facilitate scaling of MySQL databases for large scale web services.</li>
<li><a href="https://github.com/xo/usql">usql</a> - universal command-line interface for SQL databases</li>
</ul>
<p><em>SQL query builder, libraries for building and using SQL.</em></p>
<ul>
<li><a href="https://github.com/arthurkushman/buildsqlx">buildsqlx</a> - Go Database query builder library</li>
<li><a href="https://github.com/mgutz/dat">dat</a> - Go Postgres Data Access Toolkit</li>
<li><a href="https://github.com/gchaincl/dotsql">Dotsql</a> - Go library that helps you keep sql files in one place and use it with ease.</li>
<li><a href="https://github.com/doug-martin/goqu">goqu</a> - An idiomatic SQL builder and query library.</li>
<li><a href="https://github.com/Fs02/grimoire">grimoire</a> - Grimoire is a database access layer and validation for golang. (Support: MySQL, PostgreSQL and SQLite3).</li>
<li><a href="https://github.com/galeone/igor">igor</a> - Abstraction layer for PostgreSQL that supports advanced functionality and uses gorm-like syntax.</li>
<li><a href="https://github.com/go-ozzo/ozzo-dbx">ozzo-dbx</a> - Powerful data retrieval methods as well as DB-agnostic query building capabilities.</li>
<li><a href="https://github.com/volatiletech/sqlboiler">SQLBoiler</a> - a tool to generate a Go ORM tailored to your database schema. It is a &quot;database-first&quot; ORM as opposed to &quot;code-first&quot;, and you must first create your database.</li>
<li><a href="https://github.com/elgris/sqrl">sqrl</a> - SQL query builder, fork of Squirrel with improved performance.</li>
<li><a href="https://github.com/Masterminds/squirrel">Squirrel</a> - Go library that helps you build SQL queries.</li>
<li><a href="https://github.com/knq/xo">xo</a> - Generate idiomatic Go code for databases based on existing schema definitions or custom queries supporting PostgreSQL, MySQL, SQLite, Oracle, and Microsoft SQL Server.</li>
</ul>
<h2>Database Drivers</h2>
<p><em>Libraries for connecting and operating databases.</em></p>
<ul>
<li>
<p>Relational Databases</p>
<ul>
<li><a href="https://github.com/viant/bgc">bgc</a> - Datastore Connectivity for BigQuery for go.</li>
<li><a href="https://github.com/nakagami/firebirdsql">firebirdsql</a> - Firebird RDBMS SQL driver for Go</li>
<li><a href="https://github.com/mattn/go-adodb">go-adodb</a> - Microsoft ActiveX Object DataBase driver for go that using database/sql.</li>
<li><a href="https://github.com/rounds/go-bqstreamer">go-bqstreamer</a> - BigQuery fast and concurrent stream insert.</li>
<li><a href="https://github.com/denisenkom/go-mssqldb">go-mssqldb</a> - Microsoft MSSQL driver in go language.</li>
<li><a href="https://github.com/mattn/go-oci8">go-oci8</a> - Oracle driver for go that using database/sql.</li>
<li><a href="https://github.com/go-sql-driver/mysql">go-sql-driver/mysql</a> - MySQL driver for Go.</li>
<li><a href="https://github.com/mattn/go-sqlite3">go-sqlite3</a> - SQLite3 driver for go that using database/sql.</li>
<li><a href="https://github.com/minus5/gofreetds">gofreetds</a> Microsoft MSSQL driver. Go wrapper over <a href="http://www.freetds.org">FreeTDS</a>.</li>
<li><a href="https://github.com/jackc/pgx">pgx</a> - PostgreSQL driver supporting features beyond those exposed by database/sql.</li>
<li><a href="https://github.com/lib/pq">pq</a> - Pure Go Postgres driver for database/sql.</li>
</ul>
</li>
<li>
<p>NoSQL Databases</p>
<ul>
<li><a href="https://github.com/aerospike/aerospike-client-go">aerospike-client-go</a> - Aerospike client in Go language.</li>
<li><a href="https://github.com/solher/arangolite">arangolite</a> - Lightweight golang driver for ArangoDB.</li>
<li><a href="https://github.com/viant/asc">asc</a> - Datastore Connectivity for Aerospike for go.</li>
<li><a href="https://github.com/google/cayley">cayley</a> - A graph database with support for multiple backends.</li>
<li><a href="https://github.com/viant/dsc">dsc</a> - Datastore connectivity for SQL, NoSQL, structured files.</li>
<li><a href="https://github.com/underarmour/dynago">dynago</a> - Dynago is a principle of least surprise client for DynamoDB</li>
<li><a href="https://github.com/couchbase/go-couchbase">go-couchbase</a> - Couchbase client in Go</li>
<li><a href="https://github.com/fjl/go-couchdb">go-couchdb</a> - Yet another CouchDB HTTP API wrapper for Go</li>
<li><a href="https://github.com/couchbase/gocb">gocb</a> - Official Couchbase Go SDK</li>
<li><a href="http://gocql.github.io">gocql</a> - A Go language driver for Apache Cassandra.</li>
<li><a href="https://github.com/bradfitz/gomemcache/">gomemcache</a> - memcache client library for the Go programming language.</li>
<li><a href="https://github.com/GoRethink/gorethink">gorethink</a> - Go language driver for RethinkDB</li>
<li><a href="https://github.com/zegl/goriak">goriak</a> - Go language driver for Riak KV   </li>
<li><a href="https://github.com/mongodb/mongo-go-driver">mongo-go-driver</a> - The Go driver for MongoDB</li>
<li><a href="https://github.com/cihangir/neo4j">neo4j</a> - Neo4j Rest API Bindings for Golang</li>
<li><a href="https://github.com/davemeehan/Neo4j-GO">Neo4j-GO</a> - Neo4j REST Client in golang.</li>
<li><a href="https://github.com/jmcvetta/neoism">neoism</a> - Neo4j client for Golang</li>
<li><a href="https://github.com/gomodule/redigo">redigo</a> - Redigo is a Go client for the Redis database.</li>
<li><a href="https://github.com/go-redis/redis">redis</a> - Redis client for Golang</li>
<li><a href="https://github.com/hoisie/redis">redis</a> - A simple, powerful Redis client for Go.</li>
<li><a href="https://github.com/bsm/redeo">redis</a> - Redis-protocol compatible TCP servers/services.</li>
</ul>
</li>
<li>
<p>Search and Analytic Databases</p>
<ul>
<li><a href="https://github.com/blevesearch/bleve">bleve</a> - A modern text indexing library for go.</li>
<li><a href="https://github.com/olivere/elastic">elastic</a> - Elasticsearch client for Go.</li>
<li><a href="https://github.com/mattbaird/elastigo">elastigo</a> - A Elasticsearch client library.</li>
<li><a href="https://github.com/seiflotfy/skizze">skizze</a> - A probabilistic data-structures service and storage.</li>
</ul>
</li>
<li>
<p>Multiple Backends</p>
<ul>
<li><a href="https://github.com/philippgille/gokv">gokv</a> - A simple key-value store interface and many implementations for Go (Redis, Consul, etcd, bbolt, BadgerDB, LevelDB, Memcached, DynamoDB, S3, PostgreSQL, MongoDB, CockroachDB and many more)</li>
</ul>
</li>
</ul>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/98/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Latex常用数学符号</title>
		<link>https://zhangxihai.cn/archives/75</link>
					<comments>https://zhangxihai.cn/archives/75#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Sat, 31 Oct 2020 09:42:12 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<category><![CDATA[数学]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=75</guid>

					<description><![CDATA[LaTeX（LATEX，音译“拉泰赫”）是一种基于ΤΕΧ的排版系统，由美国计算机学家莱斯利·兰伯特（Leslie Lamport）在20世纪80年代初期开发，利用这种格式，即使使用者没有排版和程序设计的知识也可以充分发挥由TeX所提供的强大功能，能在几天、甚至几小时内生成很多具有书籍质量的印刷品。对于生成复杂表格和数学公式，这一点表现得尤为突出。因此它非常适...]]></description>
										<content:encoded><![CDATA[<p>LaTeX（LATEX，音译“拉泰赫”）是一种基于ΤΕΧ的排版系统，由美国计算机学家莱斯利·兰伯特（Leslie Lamport）在20世纪80年代初期开发，利用这种格式，即使使用者没有排版和程序设计的知识也可以充分发挥由TeX所提供的强大功能，能在几天、甚至几小时内生成很多具有书籍质量的印刷品。对于生成复杂表格和数学公式，这一点表现得尤为突出。因此它非常适用于生成高印刷质量的科技和数学类文档。这个系统同样适用于生成从简单的信件到完整书籍的所有其他种类的文档。</p>
<p><a href="https://blog.csdn.net/anscor/article/details/80878285" title="放个连接备用">放个连接备用</a></p>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/75/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>RabbitMQ面试题汇总</title>
		<link>https://zhangxihai.cn/archives/152</link>
					<comments>https://zhangxihai.cn/archives/152#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Fri, 22 Feb 2019 05:46:29 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<category><![CDATA[MQ]]></category>
		<category><![CDATA[Rabbitmq]]></category>
		<category><![CDATA[面试题]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=152</guid>

					<description><![CDATA[1 为什么要使用MQ？MQ和Redis模拟消息队列相比有什么优点？ 为什么要使用MQ 解耦，系统与系统之间的耦合。 异步，非必要的业务逻辑可以以异步方式运行，加快响应速度 消峰，减少并发 对比Redis消息队列 消息消费的可靠性 Redis没有相应的机制保证消息的消费，当消费者消费失败的时候，消息体丢失，需要手动处理, 例如用数据库、File等进行存储，以保...]]></description>
										<content:encoded><![CDATA[<h4>1 为什么要使用MQ？MQ和Redis模拟消息队列相比有什么优点？</h4>
<p><strong>为什么要使用MQ</strong></p>
<ol>
<li>解耦，系统与系统之间的耦合。</li>
<li>异步，非必要的业务逻辑可以以异步方式运行，加快响应速度</li>
<li>消峰，减少并发</li>
</ol>
<p><strong>对比Redis消息队列</strong></p>
<ol>
<li>消息消费的可靠性<br />
Redis没有相应的机制保证消息的消费，当消费者消费失败的时候，消息体丢失，需要手动处理, 例如用数据库、File等进行存储，以保证队列可以重新处理；</li>
</ol>
<p>MQ一般都有消费确认机制，即使消费失败，也会自动使得消息体返回原队列，同时可全程持久化，保证消息体被正确消费；</p>
<ol start="2">
<li>
<p>发布的可靠性<br />
Redis不提供发布确认，需要自行实现，而MQ通常都有发布确认功能，保证消息被发布到服务器；</p>
</li>
<li>
<p>高可用<br />
Redis故障转移方案不够完美，而MQ集群通常采用磁盘、内存节点，任意单带那故障都不会影响整个队列的操作；</p>
</li>
<li>
<p>持久化<br />
Redis是数据持久化到磁盘，并不是单独针对消息队列。MQ通常队列、消息都可以单独选择是否持久化到磁盘。</p>
</li>
<li>
<p>消费者负载均衡<br />
Redis不提供，需要自行实现，MQ通常根据消费者情况，进行消息的均衡分发；</p>
</li>
<li>
<p>队列监控<br />
Redis不提供，需要自行实现，,Q可以兼容某个队列的所有信息（内存、磁盘、消费者、生产者、速率等）。</p>
</li>
<li>
<p>流量控制<br />
不提供，需要自行实现，MQ通常早服务器过载的情况下，对生产者速率进行限制，保证服务可靠性</p>
</li>
<li>
<p>出入对性能<br />
高并发下，MQ的入队性能通常高于Redis。</p>
</li>
</ol>
<h4>2 RabbitMQ中Broker指什么，cluster又是指什么？</h4>
<p>broker是指一个或多个erlong node的逻辑分组，且node导航运行着rabbitma的应用程序。</p>
<p>cluster是再broker基础之上，增加node之间共享元数据的约束；</p>
<h4>3 RabbitMQ的消息基于什么传输?</h4>
<p>由于TCP连接的创建和小会开销较大，且并发数受系统资源限制，会造成性能瓶颈，RabbitMQ使用信道的方式来传输数据。信道是建立在真实的TCP内的虚拟连接，且每条TCP连接上的信道数量没有限制；</p>
<h4>4 RabbitMQ的消息时如何分发的？</h4>
<p>如果队列至少有一个消费者订阅，消息将以循环的方式发送给消费者。每条消息只会分发给一个订阅的消费者（前提是消费者能够正常处理消息并进行确认）；</p>
<h4>5 消息怎么路由？</h4>
<p>消息理由有三部分：交换器、路由、绑定。生产者把消息发布到交换器上，绑定决定了消息如何从路由器器路由到特定的队列；消息最终到达队列，并被消费者接收；</p>
<p>消息发布到交换器时，消息将用于一个路由键，在消息创建时设定。</p>
<p>通过队列路由键，可以把队列绑定到交换器上。</p>
<p>消息到达交换器后，RabbitMQ会将消息的路由键与队列的路由键进行匹配，如果能够匹配到队列，则消息会投递到相应的队列中； 如果不能匹配到任何队列，消息将进入黑洞。</p>
<p>常用交换器有三种：</p>
<ul>
<li><strong>direct</strong>：如果路由键完全匹配，消息就诶投递到相应的队列；</li>
<li><strong>fanout</strong>: 如果交换器收到消息，将会广播到所有绑定的队列上；</li>
<li><strong>topic</strong> 可以使来自不同源头的消息能够匹配到达同一个队列。</li>
</ul>
<h4>6 如何确保消息正确地发送至RabbitMQ</h4>
<p>Rabiitmq使用发送确认模式，确保消息正确地发送到RabbitMQ.<br />
发送确认模式：将信道设置成confirm模式（发送方确认模式），则所有在信道上发布的消息都会被指派一个唯一ID。一旦消息被投递到目的队列后，或者消息被写入磁盘后，信道会发送一个确认给生产者（包含消息唯一ID）。如果RabbitMQ内部错误从而导致消息丢失，会发送一跳未确认消息。发送方确认模式是异步的，生产者应用程序在等待确认的同事，可以继续发送消息。当确认消息到达生产者应用程序，生产者应用程序的回调方法就会被处罚来处理确认消息。</p>
<h4>7 如何保证消息接收方消费了消息？</h4>
<p>消费者接受每一条消息后都必须进行确认（消息接收和消息确认是两个不同操作）。只有消费者确认了消息，RabbitMQ才能安全第把消息从队列中删除。这里并没用用到超时机制，RabbitMQ仅通过Consumer的链接中断来确认会否需要重新发送消息。也就是说，只要链接不中断，Rabbitmq给了Consumer足够长的时间来处理消息。</p>
<p>特殊情况：</p>
<ul>
<li>如果消费者接收到消息，在确认之前断开了连接或取消订阅，RabbitMQ会认为消息没有被分发，然后重新分发给下一个订阅的消费者；</li>
<li>吐过消费者接收到消息却没有确认消息，连接也未断开，则RabbitMQ认为该消费者繁忙，将不会给消费者分发更多的消息;</li>
</ul>
<h4>8 如何避免消息重复投递或重复消费？</h4>
<p>在消息生产时，MQ内部针对每条生产者发送的消息生成一个inner-msg-id，做为去重和幂等的依据，避免重复的消息进入队列。在消息消费时，要求消息体重必须要有一个bizId做为去重和幂等的依据，避免同一消息被重复消费。</p>
<h4>9 如何解决丢数据的问题？</h4>
<p><strong>生产者丢数据</strong><br />
开启transaction和confirm模式来保证生产者不丢消息。</p>
<p>transaction类似于数据库事务，发送过程中发送异常事务就会回滚。</p>
<p>confirm是确认机制，投递成功则发一条ACK给生产者，投递失败则发一条NACK给生产者，以便重试。</p>
<p>如果是rabbitmq断连，程序员异常，则需要进行异常处理，进行本地端记录，但由于无法保证全部异常都处理， 也可以将投递的消息全部存于本地后，投递成功则标记。</p>
<p><strong>消息队列丢数据</strong><br />
开启持久化磁盘配置，配合comfirm机制，rabbitmq在持久话后，才会给生产者发送ACK。</p>
<p><strong>消费者丢数据</strong><br />
启用手动确认模式</p>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/152/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Redis面试题汇总</title>
		<link>https://zhangxihai.cn/archives/151</link>
					<comments>https://zhangxihai.cn/archives/151#respond</comments>
		
		<dc:creator><![CDATA[胖爷]]></dc:creator>
		<pubDate>Wed, 22 Feb 2017 05:44:07 +0000</pubDate>
				<category><![CDATA[其它]]></category>
		<category><![CDATA[redis]]></category>
		<category><![CDATA[面试题]]></category>
		<guid isPermaLink="false">https://zhangxihai.cn/?p=151</guid>

					<description><![CDATA[1 请说出你对Redis的认识，Redis有哪些优缺点？ Redis是一个使用C语言编写，开源的高性能非关系型数据库。 Redis有5种数据存储类型，健的类型只能是字符串，值的类型可以是：字符串、列表、集合、散列表、有序集合。 Redis的数据存储在内存之中，所以读写速度非常快，每秒可以处理超过10万次数据读写操作。 优点 读写性能优异，读速度可达11000...]]></description>
										<content:encoded><![CDATA[<h4>1 请说出你对Redis的认识，Redis有哪些优缺点？</h4>
<p>Redis是一个使用C语言编写，开源的高性能非关系型数据库。</p>
<p>Redis有5种数据存储类型，健的类型只能是字符串，值的类型可以是：字符串、列表、集合、散列表、有序集合。</p>
<p>Redis的数据存储在内存之中，所以读写速度非常快，每秒可以处理超过10万次数据读写操作。</p>
<p><strong>优点</strong></p>
<ul>
<li>读写性能优异，读速度可达110000次/秒，写速度可达到81000次/秒；</li>
<li>支持数据持久化，支持AOF和RDB两种数据持久化；</li>
<li>支持事务，Redis所有操作都是原子性的，同时Redis还支持对几个操作合并后的原子性操作；</li>
<li>数据结构丰富，除了支持string外，还支持hash、set、zset、list等数据结构；</li>
<li>支持主从复制，主机会自动将数据同步到从机，可以进行读写分离；</li>
</ul>
<p><strong>缺点</strong></p>
<ul>
<li>易受物理内存限制，不能作为海量数据的高性能读写，因此适应场景主要局限在较小数据量的高性能操作和运算上；</li>
<li>不具备容错和恢复功能，主机从机的宕机都会导致前端部分读写请求失败，需要等待机器重启或手动切换前端IP才能恢复；</li>
<li>主机宕机，宕机前有部分数据未能及时同步到从机，切换IP后还会引发数据不一致问题，降低可用性；</li>
<li>Redis较难支持在线扩容，在集群容量达到上限时在线扩容会变得很复杂。为避免这一问题，运维人员在系统上线时必须确保有足够的空间，这会对资源造成很大的浪费；</li>
</ul>
<h4>2 Redis为什么会这么快？</h4>
<ol>
<li>完全基于内存，绝大部分请求也是纯粹的内存操作，所以非常快速。数据在内存中，类似于HashMap，时间复杂度是O(1)</li>
<li>数据结构简单，所以数据操作也简单，这些数据结构是专门设计的。</li>
<li>采用单线程，这就避免了不必要的上下文切换和竞争条件，也不存在多进程或多线程导致的切换而消耗CPU，不用去考虑各种锁的问题，不存在加锁释放锁操作，没有因为可能出现死锁而出现的性能损耗；</li>
<li>使用多路I/O复用模型，非阻塞型IO；</li>
<li>使用底层模型不同，他们之间底层实现方式以及客户端之间通讯的应用协议不一样，Redis直接构建了自己的VM机制，因为一般的系统调用系统函数的话，会浪费一定的时间去移动和请求；</li>
</ol>
<h4>3 Redis有哪些数据类型，分别应用在什么场景?</h4>
<p><strong>string</strong><br />
可以存储字符串、整数、浮点数，适用于简单的健值对存储。<br />
应用场景：</p>
<ul>
<li>分布式锁</li>
<li>计数</li>
<li>序列化对象</li>
</ul>
<p><strong>hash</strong><br />
键值对集合，适用于存储结构化数据，例如对象。</p>
<p><strong>list</strong><br />
列表，可以从两端插入和弹出，按照插入顺序排序。适用于存储消息队列，有序数据。</p>
<p><strong>set</strong><br />
string无序集合，通过hash表实现。可执行交、并、差的操作，适用于例如粉丝列表等。</p>
<p><strong>zset</strong><br />
有序集合。可去重，可排序。</p>
<h4>4 Redis有哪些持久化方式？优缺点分别是什么？</h4>
<p>持久化是将内存数据写到磁盘中去，防止宕机数据丢失。</p>
<p>Rds提供了两种持久化方式，RDB和AOF</p>
<p><strong>RDB</strong><br />
快早持久化，默认持久化方式。Redis可以通过创建快照来获得存储在内存里面的数据在某个时间点上的副本，Redis创建快照后，可以对快照进行备份，可以将快照复制到其它服务器从而创建具有相同数据的服务器副本，还可以将快照留在原地以便重启服务器的时候使用。</p>
<p>redis.conf配置</p>
<pre><code>save 900 10</code></pre>
<p>在300秒之后，如果至少有10个KEY发生变化，REDIS就会自动触发BGSAVE命令创建快照。</p>
<p><strong>AOF</strong><br />
AOF持久化实时性更好，是目前主流的持久化方案，开启AOF命令：</p>
<pre><code>appendonly yes</code></pre>
<p>开启AOF持久化后每执行一条会更改Redis中的数据的命令，Redis就会将该命令写入磁盘的AOF文件。AOF文件的保存位置和RDB文件的位置相同，都是通过DIR参数设置的，默认的文件名appendonly.aof</p>
<p>AOF可以配置三种不同的持久化方式</p>
<ol>
<li>
<p>appednfsync always<br />
每次有数据修改发生时都会写入AOF文件，这种方式会严重降低Redis的速度</p>
</li>
<li>
<p>appendfsync everysec<br />
每秒钟同步一次，显式地将多个写命令同步到硬盘</p>
</li>
<li>
<p>appendfsync no<br />
让操作系统决定何时进行同步</p>
</li>
</ol>
<p>为了兼顾数据和写入性能，用户可以考虑appendfsync everysec玄子昂，让redis美妙同步一次AOF文件，Redis性能几乎没有收到任何影响。而且这样即使出现系统奔溃，用户最多只会丢失疫苗之内产生的数据。当硬盘忙于执行写入操作的时候，Redis还会优雅的放慢自己的速度以便适应硬盘的的最大写入速度。</p>
<p><strong>混合持久化</strong><br />
Redis4.0开始支持，AOF重写的时候就直接把RDB的内容写到AOF文件开头。这样做综合了RDB和AOF的有点，快速加载同时避免丢失过多的数据。缺点是，AOF里面的RDB部分是压缩格式不再是AOF格式，可读性差。</p>
<h4>5 什么是缓存雪崩和缓存穿透，如何解决？</h4>
<p><strong>缓存雪崩</strong></p>
<p>缓存同意时间大面积失效，后续请求落到数据库上，造成数据库短时间内承受大量请求而崩掉。</p>
<p>解决办法：</p>
<ul>
<li>保证redis集群的高可用性，发现有机器宕机就尽快补上，选择合适的内存淘汰策略；</li>
<li>系统上线前，对缓存进行预热；</li>
<li>让缓存的过期时间合理均匀分布；</li>
<li>加排斥锁；</li>
<li>缓存过期标记+异步刷新</li>
</ul>
<p><strong>缓存穿透</strong><br />
黑客故意请求缓存中不存在的数据，导致所有请求都落到数据库上，造成数据库短时间内承受大量请求而崩掉。</p>
<p>解决办法：</p>
<ul>
<li>最简单的办法就是将空结果进行缓存，但是不要太长时间；</li>
<li>复杂一点的办法就是使用布隆过滤器，将所有可能存在的数据哈希到一个足够大的bitmap中，不存在的数据肯定会被bitmap兰及诶啊哦。</li>
</ul>
<h4>6 如何解决Redis并发竞争Key问题？</h4>
<p>多个系统同时对一个KEY进行操作，但是最后执行的顺序和我们期望的殊勋不同，这样就导致了结果的不同。</p>
<p>解决办法：<br />
使用分布式锁。<br />
基于zookeeper临时有序节点可以实现分布式锁，大致思想为:每个客户端对某个方法加锁时，在zookeeper上的域该方法对应的指定节点的目录下，生成一个唯一的瞬时有序节点。判断是否货物所的方式很简单，值需要判断有序节点中序号最小的一个。当锁释放的时候，只需要将这个瞬时节点删除即可。同时，其可以表面服务宕机导致的锁无法释放，而产生的死锁问题。完成业务流程后，删除对应的子节点释放锁。</p>
<h4>7 Redis如何实现分布式锁？</h4>
<ol>
<li>
<p>加锁<br />
NX操作，写入随机值，设置鬼泣时间，避免死锁。</p>
</li>
<li>
<p>解锁<br />
解锁必须确保操作的原子性，所以需要借助LUA先判断随机值是否相等再解锁</p>
</li>
</ol>
<h4>8 详述Redis过期策略和内存淘汰机制？</h4>
<p><strong>定时删除</strong></p>
<ol>
<li>设置键的过期时间时，创建一个Timer, 当过期时间到临时，立刻删除键；</li>
<li>内存友好型策略，一旦键过期，就会被删除，并释放所占用的内存，CPU不友好，当一批数量比较多的键过期时，正好遇上CPU紧张的时段，这时候需要的事CPU处理能力，而不是内存。显然CPU时间用在删除过期键上，会对服务器的响应时间和吞吐量造成影响。另外当前Redis时间事件无法搞笑处理大量时间事件，所以定时删除并不是一种号的定时删除策略。</li>
</ol>
<p>Redis默认每个100ms检查，随机抽取KEY进行检查，如果过期则删除，这种操作十分消耗CPU资源。</p>
<p><strong>惰性删除</strong><br />
不管过期的键，在这种策略下，当键在空间中被取出时，首先检查取出的键是否过期，若过期删除该键，否则，返回该键；</p>
<p><strong>定期删除</strong><br />
即内存淘汰策略：</p>
<ul>
<li>noeviction ： 当内存不足以容纳新写入数据时，新写入操作会报错；</li>
<li>allkeys-lru ：当内存不足以容纳新写入数据时，在键空间红，移除最近最少使用的KEY；</li>
<li>allkeys-random : 当内存布椅子容纳新写入数据时，在键空间中，随机移除某个KEY；</li>
<li>volatile-lru ： 当内存不足以容纳写入数据时，在这是了过期时间的键空间中，移除最近最少使用的KEY。 这种情况一般是把Redis即当缓存，又做持久化存储的时候采用。</li>
<li>volatile-random： 当内存不足以容纳新写入数据时，在设置了过期时间的键空间中，有更早过期时间的KEY优先移除。</li>
</ul>
<h4>9 如何保证缓存与数据库双写时的数据一致性？</h4>
<p>数据库和缓存双鞋，就必然会存在不一致的问题。有强一致性的场景，就不能做缓存。</p>
<p>做缓存则代表取最终一致性：</p>
<ol>
<li>采取正确的更新策略，先更新数据库，再删除缓存</li>
<li>如果存在删除缓存失败，提供补偿措施，例如利用消息队列</li>
</ol>
<h4>10 Redis适合那些场景？</h4>
<ol>
<li>Sesion共享（单点登录）</li>
<li>页面缓存</li>
<li>消息队列</li>
<li>分布式锁</li>
<li>排行榜/计数器</li>
<li>发布订阅</li>
</ol>
]]></content:encoded>
					
					<wfw:commentRss>https://zhangxihai.cn/archives/151/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
