简介: 转载的文章,里面介绍的技巧用的好的话可以提高工作效率,而且有几条很实用,比如 record screen, ssh-copy-id 等等。
转载请注明出处


#1. Run the last command as root

$ sudo !!

We all know what the sudo command does - it runs the command as another user, in this case, it runs the command as superuser because no other user was specified. But what's really interesting is the bang-bang !! part of the command. It's called the event designator. An event designator references a command in shell's history. In this case the event designator references the previous command. Writing !! is the same as writing !-1. The -1 refers to the last command. You can generalize it, and write !-n to refer to the n-th previous command. To view all your previous commands, type history.

This one-liner is actually really bash-specific, as event designators are a feature of bash.

I wrote about event designators in much more detail in my article "The Definitive Guide to Bash Command Line History." The article also comes with a printable cheat sheet for working with the history.

#2. Serve the current directory at http://localhost:8000/

$ python -m SimpleHTTPServer

This one-liner starts a dedicated server hosting (web server) on port 8000 with the contents of current directory on all the interfaces (address 0.0.0.0), not just localhost. If you have "index.html" or "index.htm" files, it will serve those, otherwise it will list the contents of the currently working directory.

It works because python comes with a standard module called SimpleHTTPServer. The -m argument makes python to search for a module named SimpleHTTPServer.py in all the possible system locations (listed in sys.path and $PYTHONPATH shell variable). Once found, it executes it as a script. If you look at the source code of this module, you'll find that this module tests if it's run as a script if __name__ == '__main__', and if it is, it runs the test() method that makes it run a web server in the current directory.

To use a different port, specify it as the next argument:

$ python -m SimpleHTTPServer 8080

This command runs a HTTP server on all local interfaces on port 8080.

If you're looking for hosting your website, check out webhosting.

#3. Save a file you edited in vim without the needed permissions

:w !sudo tee %

This happens to me way too often. I open a system config file in vim and edit it just to find out that I don't have permissions to save it. This one-liner saves the day. Instead of writing the while to a temporary file :w /tmp/foobar and then moving the temporary file to the right destination mv /tmp/foobar /etc/service.conf, you now just type the one-liner above in vim and it will save the file.

Here is how it works, if you look at the vim documentation (by typing :he :w in vim), you'll find the reference to the command :w !{cmd} that says that vim runs {cmd} and passes it the contents of the file as standard input. In this one-liner the {cmd} part is the sudo tee % command. It runs tee % as superuser. But wait, what is %? Well, it's a read-only register in vim that contains the filename of the current file! Therefore the command that vim executes becomes tee current_filename, with the current directory being whatever the current_file is in. Now what does tee do? The tee command takes standard input and write it to a file! Rephrasing, it takes the contents of the file edited in vim, and writes it to the file (while being root)! All done!

Blue host and Hostgator are considered best web host in hosting industry.

#4. Change to the previous working directory

$ cd -

Everyone knows this, right? The dash "-" is short for "previous working directory." The previous working directory is defined by $OLDPWD shell variable. After you use the cd command, it sets the $OLDPWD environment variable, and then, if you type the short version cd -, it effectively becomes cd $OLDPWD and changes to the previous directory.

To change to a directory named "-", you have to either cd to the parent directory and then do cd ./- or do cd /full/path/to/-.

#5. Run the previous shell command but replace string "foo" with "bar"

$ ^foo^bar^

This is another event designator. This one is for quick substitution. It replaces foo with bar and repeats the last command. It's actually a shortcut for !!:s/foo/bar/. This one-liner applies the s modifier to the !! event designator. As we learned from one-liner #1, the !! event designator stands for the previous command. Now the s modifier stands for substitute (greetings to sed) and it substitutes the first word with the second word.

Note that this one-liner replaces just the first word in the previous command. To replace all words, add the g modifer (g for global):

$ !!:gs/foo/bar

This one-liner is also bash-specific, as event designators are a feature of bash.

Again, see my article "The Definitive Guide to Bash Command Line History." I explain all this stuff in great detail.

#6. Quickly backup or copy a file

$ cp filename{,.bak}

This one-liner copies the file named filename to a file named filename.bak. Here is how it works. It uses brace expansion to construct a list of arguments for the cp command. Brace expansion is a mechanism by which arbitrary strings may be generated. In this one-liner filename{,.bak} gets brace expanded to filename filename.bak and puts in place of the brace expression. The command becomes cp filename filename.bak and file gets copied.

Talking more about brace expansion, you can do all kinds of combinatorics with it. Here is a fun application:

$ echo {a,b,c}{a,b,c}{a,b,c}

It generates all the possible strings 3-letter from the set {a, b, c}:

aaa aab aac aba abb abc aca acb acc baa bab bac bba bbb bbc bca bcb bcc caa cab cac cba cbb cbc cca ccb ccc 

And here is how to generate all the possible 2-letter strings from the set of {a, b, c}:

$ echo {a,b,c}{a,b,c} 

It produces:

aa ab ac ba bb bc ca cb cc 

If you liked this, you may also like my article where I defined a bunch of set operations (such as intersection, union, symmetry, powerset, etc) by using just shell commands. The article is called "Set Operations in the Unix Shell." (And since I have sets in the shell, I will soon write articles on on "Combinatorics in the Shell" and "Algebra in the Shell". Fun topics to explore. Perhaps even "Topology in the Shell" :))

#7. mtr - traceroute and ping combined

$ mtr google.com

MTR, bettern known as "Matt's Traceroute" combines both traceroute and ping command. After each successful hop, it sends a ping request to the found machine, this way it produces output of both traceroute and ping to better understand the quality of link. If it finds out a packet took an alternative route, it displays it, and by default it keeps updating the statistics so you knew what was going on in real time.

#8. Find the last command that begins with "whatever," but avoid running it

$ !whatever:p

Another use of event designators. The !whatever designator searches the shell history for the most recently executed command that starts with whatever. But instead of executing it, it prints it. The :p modifier makes it print instead of executing.

This one-liner is bash-specific, as event designators are a feature of bash.

Once again, see my article "The Definitive Guide to Bash Command Line History." I explain all this stuff in great detail.

#9. Copy your public-key to remote-machine for public-key authentication

$ ssh-copy-id remote-machine

This one-liner copies your public-key, that you generated with ssh-keygen (either SSHv1 file identity.pub or SSHv2 file id_rsa.pub) to the remote-machine and places it in ~/.ssh/authorized_keys file. This ensures that the next time you try to log into that machine, public-key authentication (commonly referred to as "passwordless authentication.") will be used instead of the regular password authentication.

If you wished to do it yourself, you'd have to take the following steps:

your-machine$ scp ~/.ssh/identity.pub remote-machine: your-machine$ ssh remote-machine remote-machine$ cat identity.pub >> ~/.ssh/authorized_keys 

This one-liner saves a great deal of typing. Actually I just found out that there was a shorter way to do it:

your-machine$ ssh remote-machine 'cat >> .ssh/authorized_keys' < .ssh/identity.pub 

#10. Capture video of a linux desktop

$ ffmpeg -f x11grab -s wxga -r 25 -i :0.0 -sameq /tmp/out.mpg

A pure coincidence, I have done so much video processing with ffmpeg that I know what most of this command does without looking much in the manual.

The ffmpeg generally can be descibed as a command that takes a bunch of options and the last option is the output file. In this case the options are -f x11grab -s wxga -r 25 -i :0.0 -sameq and the output file is /tmp/out.mpg.

Here is what the options mean:

  • -f x11grab makes ffmpeg to set the input video format as x11grab. The X11 framebuffer has a specific format it presents data in and it makes ffmpeg to decode it correctly.
  • -s wxga makes ffmpeg to set the size of the video to wxga which is shortcut for 1366x768. This is a strange resolution to use, I'd just write -s 800x600.
  • -r 25 sets the framerate of the video to 25fps.
  • -i :0.0 sets the video input file to X11 display 0.0 at localhost.
  • -sameq preserves the quality of input stream. It's best to preserve the quality and post-process it later.

You can also specify ffmpeg to grab display from another x-server by changing the -i :0.0 to -i host:0.0.

If you're interested in ffmpeg, here are my other articles on ffmpeg that I wrote while ago:

PS. This article was so fun to write, that I decided to write several more parts. Tune in the next time for "The Next Top Ten One-Liners from CommandLineFu Explained" :)

Have fun. See ya!


http://www.catonmat.net/blog/top-ten-one-liners-from-commandlinefu-explained/

本文是从 The Principles of Good Programming 这篇文章翻译而来。

好的编程原则跟好的系统设计原则和技术实施原则有着密切的联系。下面的这些编程原则在过去的这些年里让我成为了一名优秀的程序员,我相信,这些原则对任何一个开发人员来说,都能让他的编程能力大幅度的提高,能让他开发出可维护性更强、缺陷更少的程序。

我不要自我重复 — 这也许是在编程开发这最最基本的一个信条,就是要告诉你不要出现重复的代码。我们很多的编程结构之所以存在,就是为了帮助我们消除重复(例如,循环语句,函数,类,等等)。一旦程序里开始有重复现象的出现(例如很长的表达式、一大堆的语句,但都是为了表达相同的概念),你就需要对代码进行一次新的提炼,抽象。
http://en.wikipedia.org/wiki/Don%27t_repeat_yourself

提炼原则 — 跟“不要自我重复原则”相关,这一原则是说“程序中任何一段具有功能性的代码在源代码文件中应该唯一的存在。”
http://en.wikipedia.org/wiki/Abstraction_principle_(programming)

保持简单 — 简单化(避免复杂)永远都应该是你的头等目标。简单的程序让你写起来容易,产生的bug更少,更容易维护修改。
http://en.wikipedia.org/wiki/KISS_principle

不要开发你目前用不到的功能 — 除非你真正需要用到它,否则不要轻易加上那些乱七八糟用不到的功能。
http://en.wikipedia.org/wiki/YAGNI

用最简单的方法让程序跑起来 — 在开发时有个非常好的问题你需要问问自己,“怎样才能最简单的让程序跑起来?”这能帮助我们在设计时让程序保持简单。
http://c2.com/xp/DoTheSimplestThingThatCouldPossiblyWork.html

不要让我动脑子 — 这实际上是Steve Krug 关于web界面操作的一本书的书名,但也适用于编程。主旨是,程序代码应该让人们花最小的努力就能读懂和理解。如果一段程序对于阅读者来说需要花费太多的努力才能理解,那它很可能需要进一步简化。
http://www.sensible.com/dmmt.html

开放/封闭原则 — 程序里的实体项(类,模块,函数等)应该对扩展行为开放,对修改行为关闭。换句话说,不要写允许别人修改的类,应该写能让人们扩展的类。
http://en.wikipedia.org/wiki/Open_Closed_Principle

为维护者写程序 — 任何值得你编写的程序在将来都是值得你去维护的,也许由你维护,也许由他人。在将来,当你不得不维护这些程序时,你对这些代码的记忆会基本上跟一个陌生人一样,所以,你最好还是当成一直在给别人写程序。一个有助于你记住这个原则的办法是“写程序时时刻记着,这个将来要维护你写的程序的人是一个有严重暴力倾向,并且知道你住在哪里的精神变态者”。
http://c2.com/cgi/wiki?CodeForTheMaintainer

最少意外原则 — 最少意外原则通常是使用在用户界面设计上,但这个原则同样适用于编写程序。程序代码应尽可能的不要让阅读者感到意外。也就是说应该遵循编码规范和常见习惯,按照公认的习惯方式进行组织和命名,不符常规的编程动作应该尽可能的避免。
http://en.wikipedia.org/wiki/Principle_of_least_astonishment

单一职责原则 — 一个代码组件(例如类或函数)应该只执行单一的预设的任务。
http://en.wikipedia.org/wiki/Single_responsibility_principle

最小化耦合关系 — 一个代码片段(代码块,函数,类等)应该最小化它对其它代码的依赖。这个目标通过尽可能少的使用共享变量来实现。“低耦合是一个计算机系统结构合理、设计优秀的标志,把它与高聚合特征联合起来,会对可读性和可维护性等重要目标的实现具有重要的意义。”
http://en.wikipedia.org/wiki/Coupling_(computer_programming)

最大化内聚性 — 具有相似功能的代码应该放在同一个代码组件里。
http://en.wikipedia.org/wiki/Cohesion_(computer_science)

隐藏实现细节 — 隐藏实现细节能最小化你在修改程序组件时产生的对那些使用这个组件的其它程序模块的影响。
http://en.wikipedia.org/wiki/Information_Hiding

笛米特法则(Law of Demeter) — 程序组件应该只跟它的直系亲属有关系(例如继承类,内包含的对象,通过参数入口传入的对象等。)
http://en.wikipedia.org/wiki/Law_of_Demeter

避免过早优化 — 只有当你的程序没有其它问题,只是比你预期的要慢时,你才能去考虑优化工作。只有当其它工作都做完后,你才能考虑优化问题,而且你只应该依据经验做法来优化。“对于小幅度的性能改进都不该考虑,要优化就应该是97%的性能提升:过早优化是一切罪恶的根源”—Donald Knuth。
http://en.wikipedia.org/wiki/Program_optimization

代码复用 — 这不是非常核心的原则,但它跟其它原则一样非常有价值。代码复用能提高程序的可靠性,节省你的开发时间。
http://en.wikipedia.org/wiki/Code_reuse

职责分离 — 不同领域的功能应该由完全不同的代码模块来管理,尽量减少这样的模块之间的重叠。 http://en.wikipedia.org/wiki/Separation_of_concerns

拥抱变化 — 这是Kent Beck的一本书的副标题,它也是极限编程和敏捷开发方法的基本信条之一。很多的其它原则都基于此观念:面对变化,欢迎变化。事实上,一些经典的软件工程原则,例如最小化耦合,就是为了让程序更容易面对变化。不论你是否采用了极限编程方法,这个原则对你的程序开发都有重要意义。http://www.amazon.com/gp/product/0321278658


From http://www.aqee.net/principles-of-good-programming/

昨天,抽风

2014年9月03日 00:00

台式机上装了个 win7 想试用一下,不小心把原来的分区全给毁了,我十几个 G 的照片阿……

1 Preface

前面曾经介绍过 GNU Global , 也提到了它没有直接支持 python 解析, 想要用它来生成 python 文件的 tags 的话,需要自己编写相应的插件。 此外, GNU Global 对 C++ 的支持程度和 C 相同, 如果两个类从包含了同名的成员函数, 在查找这个成员函数的定义时, global 不会准确的跳到相应的函数上, 还需要我们手动去选择相应的 tag 。

CEDET 是 Emacs 中的一个强大的插件,它提供了基于语义的 Tag 跳转, 该功能对 C/C++, Python, Java 等的支持都非常准确, 并且通过 mru-bookmark-mode 中的 semantic-mrub-switch-tags 提供了在多个 Tag 中来回跳转的功能。 但是, 这个跳转需要用户去指定待跳回的 Tag, 且由于默认跳转到最近一次访问的 tag , 常常会弄的很乱。

2 Solution

 新建一个栈,每次通过 semantic-ia-fast-jump 或者 semantic-ia-complete-jump 跳转的时候, 都将原 Tag 信息入栈,而每次想要跳回的时候,都从栈中 pop 出一个,并跳到刚刚 pop 出的 tag 中。

代码如下:

(require 'cedet)

;; Enable code helpers.
(semantic-load-enable-code-helpers)
(global-semantic-mru-bookmark-mode 1)

(defvar mru-tag-stack '()
  "Tag stack, when jumping to new tag, current tag will be stored here,
and when jumping back, it will be removed.")

(defun yc/store-mru-tag (pt)
  "Store tag info into mru-tag-stack"
  (interactive "d")
  (let* ((tag (semantic-mrub-find-nearby-tag pt)))
    (if tag
        (let ((sbm (semantic-bookmark (semantic-tag-name tag)
                                      :tag tag)))
          (semantic-mrub-update sbm pt 'mark)
          (add-to-list 'mru-tag-stack sbm)
          )
      (error "No tag to go!")))
  )

(defun yc/goto-func (pt)
  "Store current postion and call (semantic-ia-fast-jump)"
  (interactive "d")
  (yc/store-mru-tag pt)
  (semantic-ia-fast-jump pt)
)

(defun yc/goto-func-any (pt)
  "Store current postion and call (semantic-ia-fast-jump)"
  (interactive "d")
  (yc/store-mru-tag pt)
  (semantic-complete-jump)
  )

(defun yc/symref (pt)
  (interactive "d")
  (yc/store-mru-tag pt)
  (semantic-symref))

(defun yc/return-func()
  "Return to previous tag."
  (interactive)
  (if (car mru-tag-stack)
      (semantic-mrub-switch-tags (pop mru-tag-stack))
    (error "TagStack is empty!")))

(defun setup-program-keybindings()
  ;;;; Common program-keybindings
  (interactive)
  (local-set-key "\C-cR" 'yc/symref)
  (local-set-key "\C-cb" 'semantic-mrub-switch-tags)
  (local-set-key "\C-c\C-j" 'yc/goto-func-any)
  (local-set-key "\C-cj" 'yc/goto-func)
  (local-set-key [S-f12] 'yc/return-func)
  (local-set-key [M-S-f12] 'yc/return-func)
  (local-set-key (kbd "C-x SPC") 'yc/store-mru-tag)
  )

用法: 参考函数 setup-program-keybindings 。