[CAFFE笔记] Convolutional Layer II

卷积神经网络

上篇.说到CAFFE的牛逼CNN Layer forwarding方法,我们发现它的内存占用是个问题,而且考虑到功耗和速度的关系,不得不说这样的方法并不太适合部署在嵌入式GPU上。

要解决内存占用的问题,我们不可能回到上文提到的第一种简单粗暴的直接计算每个输出点,虽然这样可以节约整个临时矩阵Col Matrix的空间,但这种“naïve”的方法会让计算变得奇慢无比。因此,我们引入一个调节变量“set”用于控制Col Matrix的大小。理论上来说,我们要实现的效果是追求速度快的就调小set,追求内存小功耗低的,就调大set。这样,这个调节变量就可以是闲内存,速度以及功耗间的trade-off。

什么是set?

Set,简而言之就是将Col Matrix按横轴分成的等分数量。如下图。我们将要实现一种改进的算法,将ColMatrix限制在原始Col Matrix的 1/set 大小。

set

这种改进的算法,其实就是多次循环法。每次只计算一个set大小的Col Matrix块,然后生成一部分输出图像。经过多次循环,计算不同部分,最终得到完整的输出图像。如下图。

计算Col Matrix

GEMM 计算输出

现在,我们就要考虑一下这个算法到底有什么提升效果。

对于小网络来说,这样分成多个set不仅不能减少太多内存占用,而且会极大增加forwarding的时间,因为我们需要多次命令GPU执行操作,GPU启动kernel是需要一定时间的。而且对于小网络来说,set越大,每次计算的量就越少,很可能导致GPU的运算单元处于低负荷状态(有大量空闲运算资源)。因此,对于小网络来说,并没有任何优势。

对于中型网络来说,就不一样了。即使分了几个set,但并不会让GPU空闲。GPU仍然满负荷运行。而且前面提到我们可以节约1-1/set的内存,虽然不是很多,但是也还凑合。唯一浪费时间的是GPU多次启动kernel。但我们还可以从GEMM操作中节约时间。因为GEMM操作对小矩阵来说特别快,所以,比起一次算一个大矩阵,把大矩阵分成小矩阵多次算可能会出现速度提升。因此总体上来说,分1-4个set并不会浪费太多时间,还可以节约部分内存。而功耗上并不会有太大变化。另一方面,如果将set设置得很大,无疑会浪费时间,但是功耗和内存都能下降很多。对中型网络来说,具体设置多大的set,取决于对内存,速度以及功耗的需求。

对大型网络来说,即使把set设置得非常大也不会导致浪费太多时间。因为多次启动kernel的时间对于整个forwarding时间来说可以忽略了。但此时因为set比较大而节约的内存却是很大的,几百M甚至上G,这对于移动GPU来说可是福音了。在功耗上,大网络一般都会达到GPU的功耗限制,因此功耗可以说是没有变化。

总的来说,引入set这个变量,可以实现一些trade-off。具体设置成多大,要根据具体需求而定。

分享到 评论

Diario di una schiappa [Sett. Giovedì]

Diario di una schiappa

SETTEMBRE

Giovedì

Ho dei seri problemi ad abituarmi al fatto che l’estate è finita e che devo alzarmi dal letto tutte le mattine per andare a scuola.

L’estate non era iniziata esattamente alla grande, grazie a Rodrick, mio fratello maggiore.

Un paio di giorni dopo l’inizio delle vacanze, Rodrick mi ha svegliato nel cuore della notte. Mi ha detto che avevo dormito per tutta l’estate, ma che per fortuna mi ero svegliato appena in tempo per il primo giorno di scuola.

Penserete che sono stato un bel cretino a cascarci, ma Rodrick aveva addosso i vestiti di scuola e aveva messo lasveglia avanti, così sembrava mattina. E poi aveva chiuso le tende per non farmi vedere che fuori era ancora buio.

Quando Rodrick mi ha svegliato, mi sono vestito e sono sceso a prepararmi la colazione, come faccio sempre nei giorni di scuola.

Ma devo aver fatto troppo rumore perché è arrivato giù di scorsa Papà urlando che cosa diavolo ci facevo in cucina a mangiare i corn flakes alle 3.00 del mattino.

Ci ho messo un momento a capire cosa cavolo stava succedendo.

Quando l’ho capito, ho detto a Papà che Rodrick mi aveva fatto un scherzo, ed era LUI che doveva predersi la sgridata.

Papà è sceso al piano di sotto dove c’è la stanza di Rodrick, pronto a conciarlo per le feste, e io dietro. Non vedevo l’ora che si beccasse quello che meritava.

Ma Rodrick aveva un alibi di ferro. E sono sicuro che Papà è ancora convinto che io sono un po’ fuori di testa.

分享到 评论

Diario di una schiappa [Sett. Mercoledì]

Diario di una schiappa

SETTEMBRE

Mercoledì

Oggi c’era Educazione Fisica così, appena siamo usciti, per prima cosa sono corso al campo di basket per vedere se c’era ancora il Formaggio. E naturalmente era ancora lì.

Quel pezzo di Formaggio è lì sul bitume dalla primavera scorsa. Immagino che sia caduto dal panino di qualcuno. Dopo un paio di giorni il Formaggio ha cominciato ad ammuffire e a fare schifo. Nessuno voleva più giocare a basket dove c’era il Formaggio, anche se quello è l’unico campo che abbiamo con il cesto.

Poi un giorno un ragazzo che si chiama Darren Walsh ha toccato il Formaggio con un dito, e di lì è partita questa cosa della Malattia del Formaggio. In pratica è come “Ce l’hai”, ti resta addosso finché non la passi a qualcun altro.

L’unico modo per proteggersi della Malattia del Formaggio è incrociare le dita.

Ma non è mica facile ricordarsi di tenere le dita incrosciate in tutti i momenti della giornata. Alla fine me le sono legate con il cerotto a nastro così stavano incrociate tutto il tempo. Ho preso quasi sufficiente per la calligrafia, ma ne è valsa la pena.

C’era un ragazzino, Abe Hall, che si è presso la Malattia del Formaggio ad aprile e nessuno gli si è più avvicinato per il resto dell’anno. Poi Abe si è trasferito in California e si è protato dietro la Malattia del Formaggio.

Spero soltanto che nessuno faccia ripartire la Malattia del Formaggio, perché non voglio più quel genere di stress per tutta la mia vita.


Glossario

  1. corso (s.m.)
    1. Movimento regolare e continuo.
    2. Serie metodica di lezioni.
    3. Circolazione legale della moneta corrente.
    4. Quotazione dei cambi e dei titoli nella contrattazione di Borsa.
    5. Via principale.
  2. bitume (s.m.)
    1. Miscela di idrocarburi solidi o semisolidi, usata per pavimentazioni stradali o come isolante o impermeabilizzante.
  3. ammuffire (v.i.)
    1. Prendere la muffa, guastarsi per la muffa.
    2. Rimanere ostinatamente chiuso nello stesso luogo o dedicarsi in continuazione a un’attività.
  4. finché (cong.)
    1. Fino a quando.
  5. mica
    1. (s.f.) Briciola di pane; estens., minuzzolo.
    2. (avv.) Forma di negazione equivalente a ‘non’.
  6. legare (v.t.)
    1. Avvolgere per mezzo di un elemento, per lo più flessibile per garantire l’unione, il collegamento, la chiusura.
  7. cerotto (s.m.)
    1. Medicamento dotato di forti proprietà adesive, che viene spalmato su tela o altro materiale e applicato sulla cute.
    2. Persona cagionevole di salute o insistentemente molesta.
分享到 评论

无题

board

本文只是记录一下我最近的状态,不明真相的群众请绕行。

上个月在我所有网站上都装好了 Google Analytics,现在养成了每天check昨天网站访问量的习惯。其实整个网站都是很自我中心的东西,连博客都算不上是技术博客,但是竟然还是有一些来自世界各地的访问量。

最近惹上了一个特别恶心的教授,老不给我面试,整个人都很烦躁。

还有就是毕业论文,当初没好好学语文,没好好学英语,现在写个论文跟上战场一样,根本写不出东西。好羡慕那些思如泉涌的人,什么都没做也能写的龙飞凤舞的。反正就是工作多得不想做,一天无聊地闲着。

推荐一本书,叫《细说汉字》。用来学小篆不错,现在每天学10个小篆字,感觉so easy。

还有意大利语,真是怨念啊。单词记不住,别人说话听不懂,开口不会说。背课文坚持不下来,背单词坚持不下来,正常点的小说看不懂,儿童读物又嫌太弱智。真是没救了。

最近在重新看耶鲁大学的《心理学导论》公开课。倒是激起了对人工神经网络的一些思考。特别是记忆存储,遗忘过程,适应过程,焦点获取等。说实话现在的人工神经网络还有很大的提升空间。但我觉得超越人类智能的人工网络肯定能够实现。

分享到 评论

Diario di una schiappa [Sett. Martedì]

Diario di una schiappa

SETTEMBRE

Martedì

Prima di tutto voglio chiarire una cosa: Questo è un GIORNALE DI BORDO, non un diario. Lo so che sulla copertina c’è scritto diario, ma quando Mamma è andata a comprarlo le ho detto CHIARO E TONDO che ne volevo una dove non ci fosse scritto “diario”.

Appunto. Adesso manca solo che qualche idiota me lo scopra e si faccia l’idea sbagliata.

E poi voglio che sia ben chiaro che quella del diario è un’idea di MAMMA e non mia.

Ma se crede che qui ci scriva i miei “sentimenti” o chissà cosa, è pazza. Non aspettatevi niente del genere “Caro Diario” di qua e “Caro Diario” di là.

L’unica ragione per cui ho accettato di scrivere è perché ho pensato che quando sarò ricco e famoso avrò di meglioo da fare che pasare la giornata a rispondere a domande stupide. Quindi questo libro mi sarà utile.

Come dicevo, un giorno sarò famoso, ma adesso mi tocca fare le medie insieme a un mucchio di cretini.

Voglio chiarire subito che secondo me la scuola media è la cosa più stupida che sia mai stata inventata. Ci sono dei tapetti come me che non sono ancora cresciuti, insieme a dei gorilla che si devono fare la barba due volte al giorno.

E poi si stupiscono che ci sia tanto bullismo nella scuola media.

Se fossi io a decidere, farei le classi in base all’altezza e non all’età. Ma anche questa non è una soluzione, perché gente come Chirag Gupta sarebbe ancora in prima elementare.

Oggi è il primo giorno di scuola e stimano aspettando che il Prof si sbrighi a finire la piantina della classe; così ho pensato che potevo scrivere qualcosa per passare il tempo.

E a proposito di piantine, ora vi do un buon consiglio. Il primo giorno di scuola, bisogna stare molto attenti a dove ci si siede. Uno entra in classe, butta le suo cose sul primo banco che gli capita e poi si sente dire dal Prof:

SPERO CHE VI PIACCIA IL BANCO CHE AVETE SCELTO PERCHÉ SARÀ IL VOSTRO POSTO PER TUTTO L’ANNO.

Così adesso mi ritrovo bloccato con Chris Hosey davanti e Lionel James dietro.

Jason Brill è arrivato in ritardo e a momenti si sedeva accanto a me, ma per fortuna sono riuscito a evitarlo giuto in tempo.

La prossima volta dovrei cercare di sedermi in mezzo a un gruppo di ragazze carine. Ma se lo facessi, vorrebbe dire che non ho impararato niente dall’esperienza dell’anno scorso.

Accidenti, sono so cosa gli è preso alle ragazze quest’anno. Era tutto più facile alle elementari. Funzionava così: in classe quello che correva più veloce aveva tutte le ragazze per sé.

E in quinta il più veloce era Ronnie McCoy.

Adesso è tutto molto più complicato. Adesso dipende da come ti vesti o da quanto sei ricco o se hai un bel sedere o non so cosa. E i tipi come Ronnie McCoy si grattano la testa e non riescono a capire cosa cavolo è successo.

Tra i ragazzi della mia età, il più popolare è Bryce Anderson. Quello che mi dà veramente fastidio è che io sono SEMPRE stato amico delle ragazze, mentre Bryce è solo da un paio d’anni che le guarda.

Mi ricordo com’era Bryce alla elementari.

Bryce dica LE RAGAZZE SONO CACHE PUZZOLENTI!
Un altro ragazzo dica SÌÌÌÌ!
Io dico PER ME LE RAGAZZE NON SONO CACCHE PUZZOLENTI!

Ma naturalmente adesso nessuno mi riconosce il merito di essere sempre stato dalla parte delle ragazze.

Come ho già detto, Bryce è il più popolare, così tutti gli altri ragazzi stanno cercando di capire a che punto sono della classifica.

Da quello che ho potuto dedurre, io dovrei essere al 52° o 53° posto ques’anno. Ma buona notizia è che di sicuro guadagnerò una posizione perché sono subito sotto Charlie Davis che la prossima settimana si mette l’apparecchio.

Ho cerdato di spiegare questa cosa della popolarità al mio amico Rowley (che probabilmente si aggira intorno al 150°), ma mi sa che gli e entrata da un orecchio e uscita dall’altro.

分享到 评论

博客更新

今天把博客主题换了,好好整理了一下链接,重新弄好了Disqus评论系统。

-_-|||

分享到 评论

[CAFFE笔记] Convolutional Layer I

卷积神经网络

简介

在Convolutional Network(卷积神经网络)中,Convolutional Layer是最关键的层。Convolutional Layer可以被看作是一种滤波器。它通过一个设定大小的采集窗口采集某个像素点附近的像素的值,通过一个线性变换转换到输出矩阵的对应像素点上。

Convolutional Layer有两个重要的特征:

  • 稀疏连接
  • 共享参数

这两个特征也比较好理解,在对图像进行滤波操作(比如模糊操作)的时候,我们也是使用一个固定大小的窗口依次对图像的一个局部区域进行变换。当使用采样窗口时,输出像素点只取决于输入图像中其相应座标附近的像素点。也就是说,对任何一个输出点只需要连接到原图像的一个局部区域。这就是所谓的稀疏连接。另外,与滤波器类似,当我们对图像进行任何一种滤波变换时,我们理所当然地总是确保这个滤波变换函数对整个图像而言是相同的。否则,如果对部分区域进行锐化,而对另外的区域进行模糊,最终得到的图像肯定没有任何意义。要保证变换函数相同,也就是保证函数的参数相同。因此,对所有神经连接使用相同的权重和偏置也就变得理所当然了。

注意:本文只着重讲解卷积层的forwarding过程,不涉及backpropagate过程。主要的原因是我的研究任务没有涉及backpropagate,并且卷积层的backpropagate其实就只是forwarding的反向运算,并没有特别值得提及的地方。

参数

必要参数

  • num_output:滤波器的个数。在同一卷积层,我们可以设置多个不同的滤波器对同一输出图像进行特征提取。各个滤波器的参数相互独立,但连接方式相同。
  • kernel_size (或 kernel_h 和 kernel_w):窗口尺寸。这个参数定义了每个采集窗口的大小。如果使用kernel_size则定义的窗口为正方形。否则可以分别指定窗口的长宽。

推荐参数

  • weight_filter(默认类型:constant,默认值:0): 权重滤波器。

可选参数

  • bias_term(默认值:true):用于设定是否在滤波函数中加入偏置。
  • pad(或pad_h 和 pad_w,默认值:0):用于设定加在输入图像各方向上的额外像素
  • stride(或stride_h 和stride_w,默认值:1):窗口间距。用于设定两个相邻窗口的采样偏移量。如果stride=1,kernel_size=2,第一个采样窗口包含[00,01,10,11]四个点,而第二个窗口包含[01,02,11,12]四个点。
  • group(默认值:1):分组。如果这个值大于1,则第i组输入只会接入第i组输出。

Pad参数示例

Stride参数示例

CAFFE的卷积层forwarding实现

上面已经提到了,卷积层需要大量的连接,连接的数量随着输入图片尺寸和通道、输出图片通道、以及Kernel的尺寸的增大而急剧增加。即使使用稀疏连接和共享参数,当这些参数都比较大时,巨大的连接数量依然会导致整个卷积层耗费大量时间和资源进行计算。因此,为了减少计算时间,CAFFE使用了一个特别的方法来加速卷积层的计算。

首先,我们先不看CAFFE的实现过程,仅仅从卷积运算的概念来入手,我们自己就可以设计一个forwarding过程的实现。其实基本的算法并不复杂。我们知道,任何一个输出像素都取决于输入图像的一个局部区域,这个局部区域的尺寸由窗口(kernel)决定,而位置则由输出点的座标决定。对每个输出通道,我们在空白窗口上“涂上”各自的权重,然后根据需要计算的输出像素点的位置,我们使用这个窗口在输入图像的对应局部区域进行滤波操作(其实就是输入图像像素点乘以窗口上的对应权重,然后把结果统统加起来)。最后,再加上一个全局的偏置就得到输出点的值了。

我们以计算输出图像的[0,0]点为例,整个计算过程可以用下图表示:

输出像素点的计算过程

这个方法实现起来非常简单,但是它有一个致命的弱点:特别慢。为什么特别慢呢?如果你使用CPU这种并发度不高的处理器来运行,整个过程需要循环N = OutputChennel x OutputHeight x OutputWidth 次。而且整个过程没有任何可以加速的tricks。如果你使用GPU这种高度并发的处理器来运行,因为各个循环没有依赖关系,每次循环虽然都可以分配到一个thread进行运行,相比CPU的版本,速度会大大提升,但是每个thread会执行多次的读全局变量操作(获取局部输入图像像素点值),各个thread的读取的内存区域不满足形成WARP的条件,导致整个读取过程耗时大大增加。我在我自己的笔记本上做过实验,在GPU(Nvidia GForce GT630M)上执行一次GoogleNet的forwarding操作,上文提到的方法需要13秒左右,而原生的CAFFE则只需要3秒。

下面我们就来看看CAFFE到底怎么实现的。

CAFFE将整个forwarding过程分成了两部分。第一步,根据输入图像产生一个临时的矩阵(Col Matrix)。第二步,使用这个Col Matrix乘以weight矩阵,再加上bias矩阵就得到了输出图像。大家肯定想知道这个Col Matrix到底是个什么神奇的东西,为什么用它只需要再执行一个简单的矩阵就能得到输出。让我们先回忆一下前面提到的方法,我们是不是在一个局部区域执行了一个点乘操作,再把结果加到了一起。这个过程其实就跟矩阵乘法中计算一个点的操作一模一样。如果我们把输出图像看作一个矩阵,那么这个输出肯定是某个神秘矩阵乘以weight矩阵再整体加上bias矩阵得来的。而CAFFE的tricks就是将输入图像做了一个预处理(叫im2col)调整成这样一个矩阵Col Matrix。调整的过程其实也不难,其实就是用空白窗口在图像上做卷积操作,因为是空白窗口,所以不会有乘法操作,只是简单的将原始像素值复制一份而已。Col Matrix的每一个通道都对应一个输入图像通道下的一个窗口兴趣点。比如,如果输入图像由5个通道,而窗口是2x2的,那么这个Col Matrix就应该有20个通道。具体的过程可以参考下图:

CAFFE的forwarding实现过程

CAFFE这样做的好处显而易见。第一步操作,我们只需要执行赋值操作,不涉及任何复杂运算,因此运算很快。第二步操作,涉及到真正的复杂乘法和加法运算,但是因为只是矩阵乘法,因此我们可以直接调用高度优化的矩阵运算库(如blas库),这样运算速度会获得急速提升。

但是,CAFFE的方法就没有缺点吗?当然有。一个致命的缺点就是Col Matrix大得离谱。为了使其适合做矩阵乘法,Col Matrix里保存了大量冗余的输入图像信息。即使是中等尺寸的输入图像,Col Matrix也可能耗费上百MB的存储空间。这对于移动GPU来说往往是不可接受的。具体的改进方法,以后再慢慢讨论。

分享到 评论

Linux Realtek r8169 以太网卡驱动问题

Realtek

症状描述

Windows 7 与 Archlinux 双系统,网卡为 Realtek Semiconductor Co., Ltd. RTL8111/8168/8411 PCI Express Gigabit Ethernet Controller。Windows网络良好,但当切换到Linux下后,网卡LED灯不亮,系统提示以太网未连接。

解决办法

启动阶段LED不亮

Windows 与 Linux 双系统时, Realtek 8168 8169 8101 8111 网卡在启动期间会出现LED灯不亮的情况。只在Windows和Linux双系统下出现。因为Realtek官方windows驱动(2007年5月之后)默认禁用了 Wake-On-LAN功能。因此每次windows关机后,网卡即被禁用。解决办法参考Archlinux的Wiki: Realtek no link / WOL problem。我的执行了 “Enable LAN Boot ROM in BIOS/CMOS” 后网卡LED在Linux启动时开始点亮。

加载网卡后LED熄灭

当Linux启动到一定阶段,开始加载网络设置的时候,LED突然熄灭了。启动完成后仍然显示以太网未连接。这是由于Linux的Realtek驱动r8169造成的。我们需要禁用这个网卡驱动,重新安装r8168驱动。

我的解决办法是先切换到windows下,使用网络直接从Archlinux的仓库中下载r8168软件包以及该软件包的所有依赖包。(相信手动解决依赖问题对Archer来说应该没问题。)然后切换到Archlinux下,使用pacman -U <pakage>按依赖顺序安装所有的软件包。最后根据r8168的安装信息提示,执行 echo "blacklist r8169" > /etc/modprobe.d/r8169_blacklist.conf 将原来的r8169驱动禁用。重启系统后,应该就能正常连接以太网了。

分享到 评论

Use of TCE

INSTALLATION

  1. Recommended TCE version is 1.12.
  2. Recommended linux distribution is Debian 7. If you prefer Debian 8, you need to solve the dependency of WxWidget manually.
  3. TCE only works on WxWidget 2.6.* and WxWidget 2.8.*. I tried with WxWidget-3.0.* by cheating the “configure” checking process, it didn’t work. So, don’t install it on any radical distribution like Archlinux or Fedora, otherwise you need to solve the dependecncy of WxWidget manually.
  4. Before installation, install compiling tool chain first:

    1
    sudo apt-get install build-essential
  5. In case you do want to install TCE on “modern” distributuion, you need to compile the WxWidget manually.

    1. DOWNLOAD wxwidget-2.8.* from the official website.
    2. INSTALL “gtk+-2.0” and “pkg-config”.
    3. COMPILE wxwidget using classic 3-step compilation process:
      1
      2
      3
      ./configure --prefix=/usr
      make
      sudo make install
  6. Now, you can compile the TCE according to the INSTALL GUIDE, Be careful while executing “configure” process for TCE, you may get errors after cheking the Boost::System library. You need to rerun configure with command:

    1
    ./configure --prefix=$HOME/local --with-boost-libdir=/usr/lib/i386-linux-gnu
  7. All the installation process will probably take more than 6 hours.

USAGE

  1. You need to set the default EDITOR in “osed” tool, otherwise you cannot edit the behavior model since the default EDITOR is nano.
分享到 评论

使用git管理代码

什么是git

git是一个分散式版本控制软件,最初由林纳斯·托瓦兹(Linus Torvalds)创作,于2005年以GPL发布。最初目的是为更好地管理Linux内核开发而设计。
git最初的开发动力来自于BitKeeper和Monotone。git最初只是作为一个可以被其他前端(比如Cogito或Stgit[8])包装的后端而开发的,但后来git内核已经成熟到可以独立地用作版本控制。很多著名的软件都使用git进行版本控制,其中包括Linux内核、X.Org服务器和OLPC内核等项目的开发流程。
要使用git版本控制服务,无需自己搭建git服务器,网上有很多免费版本的支持git的代码托管服务,其中最著名的就是github。但是github的免费账户不能创建私有仓库,不适合正在开发或者本身并不开源的软件。因此我们使用bitbucket这个支持私有仓库的网站来托管代码。

注册流程

  1. 访问网站 https://bitbucket.org
  2. 点击Get started for free按钮。
  3. 填好信息,点击Sign up。你也可以直接使用google account注册。
  4. 收到邮件后确认注册。

初始配置

安装git

  1. 这里 可以找到git的安装教程。建议 windows 用户直接下载github的客户端,它附带了一个在windows的Powershell里运行的程序。该软件可以在 这里 找到。

创建SSH密钥对

  1. 创建ssh密钥对。具体过程参考 这里
  2. 将生成的 id_rsa.pub 文件里的内容配置到你的bitbucket账户。具体过程参考 这里

成为 espolito 团队成员

  1. 微信或邮件发给我你的bitbucket帐号。

克隆 esproj 项目

1
2
3
cd <some directory>
git clone git@bitbucket.org:espolito/esproj.git
cd esproj

修改你的默认上传用户

1
2
git config --global user.name "<your name>"
git config --global user.email <your email>

修改代码

  1. 要修改已有的文件,直接修改即可。
  2. 要添加文件,直接新建一个即可。
  3. 要删除已经被服务器同步过的文件,使用命令:
    1
    git rm <file name>

提交代码

每次完成了一部分工作要及时提交到服务器,提交的命令为:

1
2
3
4
cd <to the directory of esproj>
git add .
git commit -m "<some comments to explain your modification>"
git push -u origin master

更新代码

当其他人更新了服务器上的代码之后,你本地所保存的副本就不是最新的。因此每次开始修改代码之前一定要更新代码。更新代码的命令为:

1
git checkout

分享到 评论