gitbook 读书笔记


gitbook 简介

  1. 欢迎来使用Git, 它是一个快速的分布式版本控制系统。
  2. 以介绍Git如何存储数据为始,了解它和其它版本控制系统有何异同
  3. 介绍一些Git的基本用法,将在90%的时间都在使用的命令。
  4. Git中级用法,这些用法也许会替换掉前面的基本用法。在了解前面的基本用法后, 这些看起来像魔术一样的命令,你可能会用起来很爽。
  5. Git的高级用法,在特定的环境会非常有用,获得全面的Git知识。
  6. 学习 Git 配合脚本、部署工具、编辑器和其它工具一起工作。将Git 集成进工作环境。
  7. Git hacker :low-level documentation,包括Git 的内核和协议如何运作等等。

GIT对象模型

  1. SHA: 区分不同对象名。
  2. 对象:每个对象(object) 包括三个部分:类型,大小和内容。
  3. 与SVN的区别
  4. Blob对象: 一个blob通常用来存储文件的内容.
$ git show 6ff87c4664
  1. Tree 对象: 一个tree对象有一串(bunch)指向blob对象或是其它tree对象的指针,它一般用来表示内容之间的目录层次关系。
$ git ls-tree fb3a8bdd0ce
  1. Commit对象: "commit对象"指向一个"tree对象", 并且带有相关的描述信息; 一个“commit”只指向一个"tree",它用来标记项目某一个特定时间点的状态。它包括一些关于时间点的元数据,如时间戳、最近一次提交的作者、指向上次提交(commits)的指针等等。
$ git show -s --pretty=raw 2be7fcb476
  1. 对象模型
    commit到一个Git仓库中示意图

    你可以看到: 每个目录都创建了 tree对象 (包括根目录), 每个文件都创建了一个对应的 blob对象 . 最后有一个 commit对象来指向根tree对象(root of trees), 这样我们就可以追踪项目每一项提交内容.
  2. 标签对象: 一个标签对象包括一个对象名(即SHA1签名), 对象类型, 标签名, 标签创建人的名字("tagger"), 还有一条可能包含有签名(signature)的消息.
$ git cat-file tag v1.5.0

Git目录 与 工作目录

  1. Git目录: 是为你的项目存储所有历史和元信息的目录
$>tree -L 1
.
|-- HEAD         # 这个git项目当前处在哪个分支里
|-- config       # 项目的配置信息,git config命令会改动它
|-- description  # 项目的描述信息
|-- hooks/       # 系统默认钩子脚本目录
|-- index        # 索引文件
|-- logs/        # 各个refs的历史信息
|-- objects/     # Git本地仓库的所有对象 (commits, trees, blobs, tags)
`-- refs/        # 标识你项目里的每个分支指向了哪个提交(commit)。
  1. 工作目录:
  • 'Git目录' 一般就是指项目根目录下的'.git'目录.
  • Git的 '工作目录' 存储着你现在签出(checkout)来用来编辑的文件. 当你在项目的不同分支间切换时, 工作目录里的文件经常会被替换和删除. 所有历史信息都保存在 'Git目录'中 ; 工作目录只用来临时保存签出(checkout) 文件的地方, 你可以编辑工作目录的文件直到下次提交(commit)为止.

Git索引

Git索引是一个在你的工作目录和项目仓库间的暂存区(staging area). 有了它, 你可以把许多内容的修改一起提交(commit). 如果你创建了一个提交(commit), 那么提交的是当前索引(index)里的内容, 而不是工作目录中的内容.

  1. 查看索引
$>git status
# On branch master
# Your branch is behind 'origin/master' by 11 commits, and can be fast-forwarded.
#
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#   modified:   daemon.c
#
# Changed but not updated:
#   (use "git add <file>..." to update what will be committed)
#
#   modified:   grep.c
#   modified:   grep.h
#
# Untracked files:
#   (use "git add <file>..." to include in what will be committed)
#
#   blametree
#   blametree-init
#   git-gui/git-citool

使用 git status 命令是查看索引内容的最简单办法, 运行可看到:

  • 哪些文件被暂存了(就是在你的Git索引中);
  • 哪些文件被修改了但是没有暂存;
  • 还有哪些文件没有被跟踪(untracked).

如果完全掌握了索引(index), 你就一般不会丢失任何信息, 只要你记得名字描述信息(name of the tree that it described)就能把它们找回来.


Git 安装与初始化

Git 配置

$ git config --global user.name "zhangjun"
$ git config --global user.email "zhangjun@zhihu.com"

基本用法

获得一个Git仓库

  1. Clone一个仓库
$ git clone https://git.coding.net/staufenzhang/xsbAppTest.git
  1. 初始化一个新的仓库
    假设有一个”project.tar.gz”的压缩文件里包含了一些文件,执行命令让它置于Git的版本控制管理之下:
$ tar xzf project.tar.gz
$ cd project
$ git init

Git会输出:
Initialized empty Git repository in .git/
project目录下会有一个名叫".git" 的目录被创建,这意味着一个仓库被初始化了。


正常的工作流程

$ git add file1
$ git diff 
$ git status
$ git commit "修改注释"
$ git push

git正常的提交流程.png

git正常的撤销流程.png

分支与合并@基础

分支与合并.png
  1. 一个Git仓库可以维护很多开发分支。创建一个新的叫”experimental”的分支:
$ git branch experimental
$ git branch
>  experimental
>* master
  1. “experimental” 分支是你刚才创建的,“master”分支是Git系统默认创建的主分支。星号(“”)*标识了你当工作在哪个分支下,输入:
$ git checkout experimental
  1. 切换到”experimental”分支,先编辑里面的一个文件,再提交(commit)改动,最后切换回 “master”分支。
    切换到”experimental”分支,先编辑里面的一个文件,再提交(commit)改动,最后切换回 “master”分支。
(edit file)
$ git commit -a
$ git checkout master
  1. 你现在可以看一下你原来在“experimental”分支下所作的修改还在不在;因为你现在切换回了“master”分支,所以原来那些修改就不存在了。
    你现在可以在“master”分支下再作一些不同的修改:
(edit file)
$ git commit -a
  1. 这时,两个分支就有了各自不同的修改(diverged);我们可以通过下面的命令来合并“experimental”和“master”两个分支:
此处有疑问?$ git commit -a.png
$ git merge experimental
  1. 如果这个两个分支间的修改没有冲突(conflict), 那么合并就完成了。如有有冲突,输入下面的命令就可以查看当前有哪些文件产生了冲突:
$ git diff
  1. 当你编辑了有冲突的文件,解决了冲突后就可以提交了:
$ git commit -a
  1. 提交(commit)了合并的内容后就可查看一下:
$ gitk

执行了gitk后会有一个很漂亮的图形的显示项目的历史。

  1. 这时你就可以删除掉你的 “experimental” 分支了(如果愿意):
$ git branch -d experimental

git branch -d只能删除那些已经被当前分支的合并的分支. 如果你要强制删除某个分支的话就用git branch –D;下面假设你要强制删除一个叫”crazy-idea”的分支:

$ git branch -D crazy-idea

分支是很轻量级且容易的,这样就很容易来尝试它。


如何合并

  1. 你可以用下面的命令来合并两个分离的分支:git merge:
$ git merge branchname
  1. 这个命令把分支"branchname"合并到了当前分支里面。如有冲突(冲突--同一个文件在远程分支和本地分支里按不同的方式被修改了);那么命令的执行输出就像下面一样
$ git merge next
 100% (4/4) done
Auto-merged file.txt
CONFLICT (content): Merge conflict in file.txt
Automatic merge failed; fix conflicts and then commit the result.
  1. 在有问题的文件上会有冲突标记,在你手动解决完冲突后就可以把此文件添 加到索引(index)中去,用git commit命令来提交,就像平时修改了一个文件 一样。
    如果你用gitk ?来查看commit的结果,你会看到它有两个父分支:一个指向当前 的分支,另外一个指向刚才合并进来的分支。

解决合并中的冲突

  1. 如果执行自动合并没有成功的话,git会在索引和工作树里设置一个特殊的状态, 提示你如何解决合并中出现的冲突。
    有冲突(conflicts)的文件会保存在索引中,除非你解决了问题了并且更新了索引,否则执行 git commit都会失败:
$ git commitfile.txt: needs merge
  1. 如果执行 git status会显示这些文件没有合并(unmerged),这些有冲突的文件里面会添加像下面的冲突标识符:
<<<<<<< HEAD:file.txt
Hello world
=======
Goodbye
>>>>>>> 77976da35a11db4580b80ae27e8d65caf5208086:file.txt
  1. 你所需要的做是就是编辑解决冲突,(接着把冲突标识符删掉),再执行下面的命令:
$ git add file.txt
$ git commit

注意:提交注释里已经有一些关于合并的信息了,通常是用这些默认信息,但是你可以添加一些你想要的注释。
上面这些就是你要做一个简单合并所要知道的,但是git提供更多的一些信息来帮助解决冲突。


撒销一个合并

  1. 如果你觉得你合并后的状态是一团乱麻,想把当前的修改都放弃,你可以用下面的命令回到合并之前的状态:
$ git reset --hard HEAD

或者你已经把合并后的代码提交,但还是想把它们撒销:

$ git reset --hard ORIG_HEAD

但是刚才这条命令在某些情况会很危险,如果你把一个已经被另一个分支合并的分支给删了,那么 以后在合并相关的分支时会出错。

快速向前合并

  1. 还有一种需要特殊对待的情况,在前面没有提到。通常,一个合并会产生一个合并提交(commit), 把两个父分支里的每一行内容都合并进来。
  2. 但是,如果当前的分支和另一个分支没有内容上的差异,就是说当前分支的每一个提交(commit)都已经存在另一个分支里了,git 就会执行一个“快速向前"(fast forward)操作;git 不创建任何新的提交(commit),只是将当前分支指向合并进来的分支。

查看历史 -Git日志

$ git log
  1. 日志统计
    如果用--stat选项使用'git log',它会显示在每个提交(commit)中哪些文件被修改了, 这些文件分别添加或删除了多少行内容.
$ git log --stat
git log --stat.png
  1. 格式化日志
  • 你可以按你的要求来格式化日志输出。‘--pretty'参数可以使用若干表现格式,如‘oneline':
$ git log --pretty=oneline
  • 或者你也可以使用 'short' 格式:
$ git log --pretty=short
  • 你也可用‘medium','full','fuller','email' 或‘raw'. 如果这些格式不完全符合你的相求, 你也可以用‘--pretty=format'参数(参见:git log)来创建你自己的"格式“.
$ git log --pretty=format:'%h was %an, %ar, message: %s'
  • 另一个有趣的事是:你可以用'--graph'选项来可视化你的提交图(commit graph),就像下面这样:
$ git log --pretty=format:'%h : %s' --graph

它会用ASCII字符来画出一个很漂亮的提交历史(commit history)线。

  1. 日志排序
  • 按默认情况,提交(commits)会按逆时间(reverse chronological)顺序显示。

  • 但是你也可以指定‘--topo-order'参数,这就会让提交(commits)按拓朴顺序来显示(就是子提交在它们的父提交前显示). 如果你用git log命令按拓朴顺序来显示git仓库的提交日志,你会看到“开发线"(development lines)都会集合在一起.

$ git log --pretty=format:'%h : %s' --topo-order --graph
  • 你也可以用'--date-order'参数,这样显示提交日志的顺序主要按提交日期来排序. 这个参数和'--topo-order'有一点像,没有父分支会在它们的子分支前显示,但是其它的东东还是按交时间来排序显示。你会看到"开发线"(development lines)没有集合一起,它们会像并行开发(parallel development)一样跳来跳去的:
$ git log --pretty=format:'%h : %s' --date-order --graph
  • 最后,你也可以用 ‘--reverse'参数来逆向显示所有日志。

比较提交 - Git Diff

  1. 你可以用 git diff 来比较项目中任意两个版本的差异。
$ git diff master..test

上面这条命令只显示两个分支间的差异,如果你想找出‘master’,‘test’的共有 父分支和'test'分支之间的差异,你用3个‘.'来取代前面的两个'.' 。

  1. 哪些内容会被提交(commit)
    如果你要看在下次提交时要提交的内容(staged,添加到索引中),你可以运行:
$ git diff --cached

上面的命令会显示你当前的索引和上次提交间的差异;这些内容在不带"-a"参数运行 "git commit"命令时就会被提交。

$ git diff HEAD

上面这条命令会显示你工作目录与上次提交时之间的所有差别,这条命令所显示的 内容都会在执行"git commit -a"命令时被提交。

  1. 更多的比较选项
  • 如果你要查看当前的工作目录与另外一个分支的差别,你可以用下面的命令执行:
$ git diff test
  • 这会显示你当前工作目录与另外一个叫'test'分支的差别。你也以加上路径限定符,来只 比较某一个文件或目录。
$ git diff HEAD -- ./lib 
  • 如果不是查看每个文件的详细差别,而是统计一下有哪些文件被改动,有多少行被改 动,就可以使用‘--stat' 参数。
$>git diff --stat

分布式的工作流程

  1. 假设Alice现在开始了一个新项目,在/home/alice/project建了一个新的git 仓库(repository);另一个Bob的工作目录也在同一台机器,他要提交代码。
    Bob 执行了这样的命令:
$ git clone /home/alice/project myrepo

这就建了一个新的叫"myrepo"的目录,这个目录里包含了一份Alice的仓库的 克隆(clone). 这份克隆和原始的项目一模一样,并且拥有原始项目的历史记 录。

  1. Bob 做了一些修改并且提交(commit)它们:
(edit files)
$ git commit -a
(repeat as necessary)
  1. 当他准备好了,他告诉Alice从仓库/home/bob/myrepo中把他的修改给拉 (pull)下来。她执行了下面几条命令:
$ cd /home/alice/project
$ git pull /home/bob/myrepo master
  • 这就把Bob的主(master)分支合并到了Alice的当前分支里了。
  • 如果Alice在 Bob修改文件内容的 同时 也做了修改的话,她可能需要手工去修复冲突**. (注意:"master"参数在上面的命令中并不一定是必须的,因为这是一个 默认参数)
  1. git pull命令执行两个操作: 它从远程分支(remote branch)抓取修改 的内容,然后把它合并进当前的分支。
    如果你要经常操作远程分支(remote branch),你可以定义它们的缩写:
$ git remote add bob /home/bob/myrepo
  1. 这样,Alic可以用"git fetch"" 来执行"git pull"前半部分的工作, 但是这条命令并不会把抓下来的修改合并到当前分支里。
$ git fetch bob
  1. 我们用 git remote 命令建立了Bob的运程仓库的缩写,用这个(缩写) 名字我从Bob那得到所有远程分支的历史记录。在这里远程分支的名字就叫bob/master
$ git log -p master..bob/master

上面的命令把Bob从Alice的主分支(master)中签出后所做的修改全部显示出来。

  1. 当检查完修改后,Alice就可以把修改合并到她的主分支中。
$ git merge bob/master

这种合并(merge)也可以用pull来完成,就像下面的命令一样:

$ git pull . remotes/bob/master

注意:git pull 会把远程分支合并进当前的分支里,而不管你在命令 行里指定什么。

  1. 其后,Bob可以更新它的本地仓库--把Alice做的修改拉过来(pull):
$ git pull
  1. 如果Bob从Alice的仓库克隆(clone),那么他就不需要指定Alice仓库的地 址;因为Git把Alice仓库的地址存储到Bob的仓库配库文件,这个地址就是 在git pull时使用:
$ git config --get remote.origin.url/home/alice/project

(如果要查看git clone创建的所有配置参数,可以使用"git config -l", git config 的帮助文件里解释了每个参数的含义.)
Git同时也保存了一份最初(pristine)的Alice主分支(master),在 "origin/master"下面.

$ git branch -r origin/master
  1. 如果Bob打算在另外一台主机上工作,他可以通过ssh协议来执行"clone" 和"pull"操作:
$ git clone alice.org:/home/alice/project myrepo
  • git有他自带的协议(native protocol),还可以使用rsync或http; 你可以点 这里 git pull 看一看更詳細的用法。
  • Git也可以像CVS一样来工作:有一个中心仓库,不同的用户向它推送(push) 自己所作的修改;

公共Git仓库

  1. 另外一个提交修改的办法,就是告诉项目的维护者(maintainer)用 git pull 命令从你的仓库里把修改拉下来。这和从主仓库"里更新代码类似,但是是从 另外一个方向来更新的。
  • 如果你和维护者(maintainer)都在同一台机器上有帐号,那么你们可以互相从对 方的仓库目录里直接拉(pull)所作的修改;git命令里的仓库地址也可以是本地 的某个目录名:
$ git clone /path/to/repository$ git pull /path/to/other/repository
  • 也可以是一个ssh地址:
$ git clone ssh://yourhost/~you/repository
  • 如果你的项目只有很少几个开发者,或是只需要同步很少的几个私有仓库, 上面的方法也许够你用的。
  1. 然而,更通用的作法是维护几个不同的公开仓库(public repository).这样可以把每个人的工作进度和公开仓库清楚的分开。
  • 你还是每天在你的本地私人仓库里工作,但是会定期的把本地的修改推(push) 到你的公开仓库中;其它开发者就可以从这个公开仓库来拉(pull)最新的代码。 如果其它开发者也有他自己的公共仓库,那么他们之间的开发流程就如下图 所示:
                        you push
  your personal repo ------------------> your public repo
    ^                                     |
    |                                     |
    | you pull                            | they pull
    |                                     |
    |                                     |
    |                   they push             V
  their public repo <------------------- their repo

将修改推到一个公共仓库

  1. 通过http或是git协议,其它维护者可以抓取(fetch)你最近的修改,但是他们 没有写权限。这样,这需要将本地私有仓库的最近修改上传公共仓库中。
  • 译者注: 通过http的WebDav协议是可以有写权限的,也有人配置了git over http.
  • 最简单的办法就是用 git push命令 和ssh协议; 用你本地的"master" 分支去更新远程的"master"分支,执行下面的命令:
$ git push ssh://yourserver.com/~you/proj.git master:master

或是:

$ git push ssh://yourserver.com/~you/proj.git master
  • 和git-fetch命令一样git-push如果命令的执行结果不是"快速向前"(fast forward) 就会报错; 下面的章节会讲如何处理这种情况.
  1. 推(push)命令的目地仓库一般是个裸仓库(bare respository). 你也可以推到一 个签出工作目录树(checked-out working tree)的仓库,但是工作目录中内 容不会被推命令所更新。如果你把自己的分支推到一个已签出的分支里,这 会导致不可预知的后果。
  • 在用git-fetch命令时,你也可以修改配置参数,让你少打字:)。
    下面这些是例子:
$ cat >>.git/config <<EOF
[remote "public-repo"]
    url = ssh://yourserver.com/~you/proj.git
EOF
  • 你可以用下面的命令来代替前面复杂的命令:
$ git push public-repo master

当推送代码失败时要怎么办

  1. 如果推送(push)结果不是"快速向前"(fast forward),那么它 可能会报像下面一样的错误:
error: remote 'refs/heads/master' is not an ancestor of
local  'refs/heads/master'.
Maybe you are not up-to-date and need to pull first?
error: failed to push to 'ssh://yourserver.com/~you/proj.git'
  1. 这种情况通常由以下的原因产生:
  • git-reset --hard 删除了一个已经发布了的一个提交,或是

  • git-commit --amend 去替换一个已经发布的提交,或是

  • git-rebase 去rebase一个已经发布的提交.

  1. 你可以强制git-push在上传修改时先更新,只要在分支名前面加一个加号。
$ git push ssh://yourserver.com/~you/proj.git +master
  1. 通常不论公共仓库的分支是否被修改,他都被修改为指向原来指向的提交(commit) 跟随的下一个提交(commit)。如果在这种情况下强制地推送,你就破坏了之前的约定。

  2. 尽管如此,这也是一种通常的用法来简单地发布一系列正在修正的补丁,并且只要你 通知了其他的开发者你打算怎样操作这个分支,这也是一种可以接受的折中办法。

  3. 一个推送(push)也可能因为其他人有向这个仓库(repository)推送的权利而失败。 在这种情况下,正确地解决办法是首先用"pull"命令或者"fetch"命令和"rebase" 命令更新你的代码,然后重新尝试推送(push);


Git标签

  1. 轻量级标签
    我们可以用 git tag不带任何参数创建一个标签(tag)指定某个提交(commit):
$ git tag stable-1 1b2e1d63ff
  • 这样,我们可以用stable-1 作为提交(commit) "1b2e1d63ff" 的代称(refer)。
  • 前面这样创建的是一个“轻量级标签",这种分支通常是从来不移动的。
  • 如果你想为一个标签(tag)添加注释,或是为它添加一个签名(sign it cryptographically), 那么我们就需要创建一个 ”标签对象".
  1. 标签对象
  • 如果有 "-a", "-s" 或是 "-u " 中间的一个命令参数被指定,那么就会创建 一个标签对象,并且需要一个标签消息(tag message). 如果没有"-m " 或是 "-F " 这些参数,那么就会启动一个编辑器来让用户输入标签消息(tag message).
  • 译者注:大家觉得这个标签消息是不是提交注释(commit comment)比较像。
  • 当这样的一条命令执行后,一个新的对象被添加到Git对象库中,并且标签引用就指向了 一个标签对象,而不是指向一个提交(commit). 这样做的好处就是:你可以为一个标签 打处签名(sign), 方便你以后来查验这是不是一个正确的提交(commit).
    下面是一个创建标签对象的例子:
$ git tag -a stable-1 1b2e1d63ff
  • 标签对象可以指向任何对象,但是在通常情况下是一个提交(commit). (在Linux内核代 码中,第一个标签对象是指向一个树对象(tree),而不是指向一个提交(commit)).
  1. 签名的标签
  • 如果你配有GPG key,那么你就很容易创建签名的标签.首先你要在你的 *.git/config 或 *~.gitconfig里配好key.
    下面是示例:
[user] 
       signingkey = <gpg-key-id>
  • 你也可以用命令行来配置:
$ git config (--global) user.signingkey <gpg-key-id>
  • 现在你可以直接用"-s" 参数来创“签名的标签”。
$ git tag -s stable-1 1b2e1d63ff
  • 如果没有在配置文件中配GPG key,你可以用"-u“ 参数直接指定。
$ git tag -u <gpg-key-id> stable-1 1b2e1d63ff

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 206,723评论 6 481
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 88,485评论 2 382
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 152,998评论 0 344
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 55,323评论 1 279
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 64,355评论 5 374
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,079评论 1 285
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,389评论 3 400
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,019评论 0 259
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 43,519评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,971评论 2 325
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,100评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,738评论 4 324
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,293评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,289评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,517评论 1 262
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,547评论 2 354
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,834评论 2 345

推荐阅读更多精彩内容

  • 1. 安装 Github 查看是否安装git: $ git config --global user.name "...
    Albert_Sun阅读 13,632评论 9 163
  • 已经有X个小伙伴说我头像丑了,我来和你讲一讲它的故事吧。 那是2011年夏天,鼓浪屿。行走在小岛上的我完美的避开了...
    能小姐的小啰嗦阅读 297评论 0 0
  • 首先要拿到图片的网络地址(本地图片就没什么意思了),然后根据下面这个方法获取图片的缓存地址: 记住,这个方法要在子...
    24K纯帅豆阅读 18,596评论 5 13
  • “小鱼,我跟你说,我有名字了”清晨垂首望着清泉里的游摆的鱼儿,话语间满是兴奋“是一个人给我取的名字,他居然能...
    鲸友馆阅读 307评论 2 2
  • 这周结束了,我要做总结了。 周一很普通,没啥可说的。周二我们上葫芦丝而且还学了两手曲子。我都会了。很难的班里面没几...
    张煜梒1阅读 166评论 0 0