わさっきhb

大学(教育研究)とか ,親馬鹿とか,和歌山とか,とか,とか.

領域指定7つの方法

はじめに

大学で,プログラミング授業を何科目か担当しています.
演習室で,学生の挙動を見ているとき,「そこはこうすればいいのに」と,もどかしさを覚えることがあります.BackSpaceの長押しで,数行分を削除する光景は,最たるものです.その実情と対策は,これまで,いける学生・あかん学生(プログラミング)BackSpace長押しやめましょうで書いています.
編集しているテキストの中で,領域選択をしてからカットすれば,再利用ができます.本エントリでは,Emacsを用いた領域(リージョン)の選択方法を,スクリーンショットを交えて紹介したいと思います.
なお,スクリーンショットは,Windows + NTEmacs (GNU Emacs 23.2.1 (i386-mingw-nt6.1.7601) of 2010-07-02 on ROCKERS)で取得しました.Vine Linux 6 + Emacs23でも,動作確認を行っています.

準備

「C-M-%」と書かれたとき,どんな操作をすればいいかを知っている人は,準備を読み飛ばしていただいて結構です.
本エントリで想定する読者は,授業でEmacsを使用してプログラム作成をしている学生です.Emacsの起動と終了,入力,保存が(キーボードまたはマウスから)できることを最低条件とします.
基本技に入る前に,以下のルールを理解*1してください.「Ctrlと刻印されたキーを押しながら,Aと刻印されたキーを1回押す」という操作を,C-aと略記します(コントロール・エーと呼ぶといいでしょう).2つのキーを押しますが,これは1回の操作と見なされます.Windowsのショートカットキーのようなものです.
連続するキー操作が,一つのコマンドをなすこともあります.その際,間に空白を入れて表記しますが,その空白は,打ち込みません.また「C-」の有無にも注意してください.「C-x C-j」は「Ctrlを押しながら,Xキー,Jキーの順に押す」なのに対して,「C-x j」は「Ctrlを押しながらXキーを押し,Ctrlも離して,Jキーを押す」となります.なお,標準設定では,C-x C-jもC-x jも無効(無害)な操作です.
Altキーを押しながら,他のキーを押すという操作も,よく行われます.「Altと刻印されたキーを押しながら,Aと刻印されたキーを1回押す」のは,M-aと略記します(メタ・エーと呼びます.Emacsが初期に開発・使用されたころのキーボードにはMetaキーがあった,と理解してください).この「M-」は,Escキーでも代用できます.ただし,「Altを押しながら」は「Escを押して(そして離して)から」に読み替えてください*2.本エントリでは使用しませんが,「CtrlとAltを押しながら」という操作もあり,「C-M-1文字」で略記します.Escを押してから「C-1文字」とするのと,キー操作としては等価です.
上で「コマンド」と書きましたが,Emacsに影響を与えることのできるコマンドの多くは,1回または連続する複数個のキー操作に結びつけられています(「キーバインド」とも言います).αの操作にβというコマンドに結びつけられていることを,「αのコマンドはβである」と略記することがあります*3
キーバインドを忘れてしまった(または結びつけられていない)けれど,コマンド名は知っているというときは,まずM-xとし,次にコマンド名を打ち込んで,最後にEnterキーを押せば,そのコマンドを実行します.C-M-%(日本語キーボードでは,CtrlとShiftとAltを押しながら,テンキーでない方の5を押す)は,M-x query-replace-regexpと等価です.
スペースキーは「SPC」,Enterキーは「RET」,Esc(エスケープ)キーは「ESC」と書かれます.
操作をしていて訳がわからなくなったら,ブレーキをかけましょう.C-gです.これを連打する(Ctrlを押しながら,Gのキーを何度も叩く)ことで,操作上のトラブルから回避できることもあります.

基本技1. マウスのドラッグ

準備でキー操作ばかり書きましたが,マウスでテキストをドラッグするのは,もっとも手軽な領域選択の方法です.
まず領域の先頭文字にマウスカーソルを合わせます.

そして左ボタンを押したまま,マウスを動かせば,背景色がつきます.

マウスのボタンを離せば,領域が確定します.
他の基本技と異なり,この操作だけで,領域をコピーしたことになります.したがって,後述のC-wやM-wをすることなく,使用しているEmacsもしくは他のアプリケーションで貼り付け(ペースト)ができます.

基本技2. C-SPC

Emacsでキーボードを使うとき,領域選択を始める操作は,C-SPCです.コマンドは,set-mark-commandです.
適当な箇所にカーソルを置いて,C-SPCとしてみます.

なのですが,この時点では表示は変わりません*4
そしてキーボードの操作でカーソルを動かすと,領域が選択されているのが分かります.

「ここからここまでを切り貼りしたい」という領域になったら,次のどちらかの操作をします.C-wとすると,領域が切り取られます.「カットアンドペースト」でいうところの「カット」の操作で,コマンドはkill-regionです.

代わりにM-wとすると,領域の表示がなくなりますが,内容は変わりません.「コピーアンドペースト」の「コピー」に相当し,コマンドはkill-ring-saveとなります.

カットまたはコピーした文字列は,同じEmacsならC-yで,他のアプリケーションでも貼り付ける操作により,再利用や複製ができます.

基本技3. Shiftを押しながら,上下左右

Microsoft OfficeのWordやPowerPoint,またブラウザでのテキスト入力と同様に,Shiftを押しながらカーソルキーで,領域を選択できます.
任意の位置で,Shiftを押しながら,→のキーを押すと,1文字だけ色がつきます.

何文字でも増やせますし,上下左右,任意の方向に行けます.
Shiftキーを離して,カーソルを移動させるか,何か打ち込むか,他のコマンドを実行すると,領域選択が見えなくなります*5
そしてカット(C-w)またはコピー(M-w)を選択するか,領域が不要なら停止(C-g)させましょう.以下では,領域選択後の行動について説明を割愛します.

基本技4. M-@

単語をコピーするとき,C-SPCとして,カーソルを移動させて…というのは,面倒なものです.実は単語を領域選択するキー操作があります.
まず,単語の先頭にカーソルを移動させます.

次に,M-@とします.コマンドは,mark-wordです.なお,手元のNTEmacsでは,「Altを押しながら@」は,,すなわち「半角/全角 漢字」のキーと認識される*6ので,代わりに「ESC @」と打ち込んでいます.Vine Linux上では,この不具合はなさそうです.
すると,単語が選択されます.

より具体的には,カーソルのある位置から,単語区切りの文字の前までが,選択されます.また,カーソルは移動しません.
このとき,再度M-@とすると,次の単語までを領域とします.

ファイルの終わりに至るまで,いくらでも伸ばせます.また日本語テキストに対しても,この操作で,適当に語の終わりを判断してくれて,領域選択ができます.

基本技5. C-x h

編集対象全体をコピーするには,どうしましょうか.先頭に移動して,C-SPCで,末尾に移動…大変ですね.
コマンド一発で,できます.カーソルがどこにあっても,C-x hとします.コマンドはmark-whole-bufferです.

これで,カーソルが先頭に移動し,全体を選択します.

基本技6. M-h

ファイル全体は大きすぎるので,カーソルを含む,前後の近いところだけを選択することにします.
「近いところ」を区切るのは,空行です.見た目に何も書かれていない行です*7.テキストファイルの慣習として,空行から空行までの内容は「段落」とみなされます.そして,段落を選択するコマンドがあります.
キーとしてはM-h,コマンドはmark-paragraphです.

カーソルよりも前(たいていは上)にある中で,最も近い空行の始まりのところに,カーソルが移動します.そしてそこから,後ろ(下)方向に見ていって,最初に遭遇する空行の直前までを選択します.
もし,前/後ろに空行がなければ,編集対象の先頭から/末尾までとなります.

基本技7. C-x C-p

この基本技を解説するには,テキストファイルにおける「ページ区切り」の概念が必要になります.
Microsoft Wordだと,メニューからの操作で,「ページ区切り」を入力することができますが,テキストファイルにおいては,16進2桁で0Cによって表される1バイトコードを,行頭に置くことで,ページ区切りとする慣習があります.
Emacsではこの文字を,「^L」として表示します.ただし「^」と「L」の2文字ではなく,これで1文字(1バイト)です.入力するには,C-q C-lとします.実際にはC-qのみがコマンドで,これにより,次のC-l(コントロール・エル)の文字コードを,コマンドではなく,テキストファイルへの1文字挿入とみなします.
下のように,文字列と「^L」を打ち込むとともに,カーソルを置くとします.

このとき,C-x C-pとします.コマンドはmark-pageです.
すると,前のページ区切りから,次のページ区切りまでを選択し,カーソルはその領域の先頭へ移動します.

基本技6と同様に,カーソルより前・後ろにページ区切りがなければ,編集対象の先頭から・末尾までとなります.

メモ1. マークとポイント

ここまで書いた基本技のコマンドを実行したり,カーソルを移動させたりしたとき,選択領域がどのようになるのかをきちんと理解するには,「マーク」と「ポイント」の概念を知ることが不可欠です.
領域(リージョン)とは,マークとポイントの間を言います.
そして,ポイントは,カーソルの文字のすぐ手前にあります.直前の文字,ではなく,今の文字と直前の文字の間,と考えましょう.もちろん,カーソルの移動に伴い,ポイントの位置も変わります.
次に,マークというのは,領域指定をしますよ(始めますよ)という操作をしたときに,設定されます.これも基本的には,文字と文字の間になります*8.基本技2を例にとると,C-SPCとしたとき,その時点のポイントが,マークとなります.ただしその後,カーソル(したがってポイント)が動いても,マークは動きません.そのおかげで,「マークとポイントの間」ができ,それが選択領域となる,というわけです.
マークとポイント(それとカーソル)の位置関係として,次の2種類があります.まずは,マークよりも後ろにポイントがある場合です.

マークよりも前にポイントがある場合,というのも考えられます.

基本技6でM-hとしたとき,段落の終了(後ろ方向の直近の空行の直前)のところにマークが,段落の開始(前方向の直近の空行の直前)のところにポイントがついて,そのポイントに合うよう,カーソルが移動します.
他の基本技でも,同様に,マークとポイントがどうなるか,考えてみてください.

裏技1. C-kのあとundo

ここからは,領域選択のためのコマンドではないのですが,知っておくと得する操作を書いていきます.
C-kは,kill-lineというコマンドです.行の先頭または途中であれば,そこから行末(改行コードを含まない)をカットします.行末にあれば,改行コードをカットします.
C-kの直後に,C-/とすると,カットする前に戻ります.C-/は,undoのコマンドに結びつけられています.編集内容は,アンドゥですが,カットした内容は,保持されています.
したがって,C-k C-/とすれば,内容は変更しないまま,行末までをコピーすることができるのです.
画面は例えば次のようになります.



改行まで含めてコピーしたければ…C-k C-k C-/ C-/を試してみてください.

裏技2. C-x C-x

領域に背景色表示がついていたけれども,何か操作をして消えてしまったときに,復活させる操作があります.
C-xを2回行う(実際には,Ctrlを押しながら,Xキーを2回ですね)と,カーソルが移動します.


C-x C-xは,exchange-point-and-markというコマンドになっていて,ポイントとマークを交換します.副次的な効果として,ポイントに合わよう,カーソルが移動します.それと,背景色表示が復活します.
さらにC-xを2回行うと,もう一度,ポイントとマークを交換します.もちろん,背景色表示はそのままです.

したがって,C-xを4回---C-x C-x C-x C-xとすることで,編集することなく,領域に背景色表示がなされ,それによって,マークがどこにあるかが分かるというわけです.

裏技3. 先行マーク

通常は,文書なりプログラムコードなりがあるときに,その一部を領域として選択します.なのですが,まだ形にはなっていないけれども,これから打ち込む内容(単語,文字列,行など)をコピーする必要がありそうなとき,打ち込む前から,マークをつけることはできないでしょうか.
できます.C-SPCでマークを設定してから,打ち込めばいいのです.


領域を示す背景色表示はありませんが,マークは動かず,ポイントは動きますので,領域はできています.C-wも,M-wも,裏技2のC-x C-x C-x C-xも有効です.
この先行マークを適切なタイミングで使えば,打ち込んでから領域の先頭にカーソルを移動させてC-SPCなどを押すだとか,マウスで操作するだとかいった必要がなくなります.

メモ2. 対応表

本エントリの用語 Emacsでの用語・表記
Altを押しながら M-
Ctrlを押しながら C-
Enterキー RET
Escキー, エスケープキー ESC
Escを押してから M-
アンドゥ undo
カーソル cursor
カット kill, kill-region
キー操作, ショートカットキー キーバインド, keybinding
コピー kill-ring-save
コマンド command
スペースキー SPC
ページ page
ペースト, 貼り付け yank
ポイント point
マーク mark
領域, 選択領域 リージョン, region
段落 paragraph
背景色表示 マークが活性, the mark is active*9
半角/全角 漢字
編集対象, 編集内容 バッファ, buffer

メモ3. 参考文献ほか

用語と基本操作は,『入門 GNU Emacs 第3版』を参照しました.ポイントとカーソルを使い分ける必要性についてはpp.83-84に記述があります.そこから,「マークはバッファごとに一つ」「ポイントはウィンドウごと*10に一つ」「カーソルはEmacsプロセスで一つ」と学びました.
本エントリの内容をより詳しく解説しているWebページとして,http://www.bookshelf.jp/texi/emacs-20.6-man-jp/emacs_10.htmlがあります.背景色表示のメカニズムとして,「暫定マーク」の概念がありますが,ここではその名称の紹介にとどめます.
バッファの内容は,KANのTOKYOMANの一節です.歌詞はhttp://music.goo.ne.jp/lyric/LYRUTND52126/index.htmlのものを参照しました.昨日のエントリを書きながら聞いた曲でして,リリース直後にhttp://twitter.com/takehikom/status/139063207649230850と書いています.

*1:Emacsの学習で,教わったことがないはずはないので,「確認」「復習」といったほうがいいでしょうね.

*2:Emacsでは,「Altを押して(そして離して)から」という操作はありません.

*3:キー操作からコマンドは,ただ一つ定まります.細かいことを言うと,モードが異なれば,同一のキー操作でもコマンドが異なるということは起こり得ますが,「コマンドはただ一つ定まる」のは変わりません.逆に,あるコマンドをするためのキーバインドは,一つとは限りません.例えば,C-SPCとC-@はともに,set-mark-commandとなります.

*4:最下段に「Mark set」または「Mark activated」と出ます.すでに領域選択をしているときに,この操作をすると,領域の表示(背景色)がなくなります.

*5:実際には,領域の開始位置は保持されています.後述の「マーク」「ポイント」の言葉を使うと,Shift+カーソルキーの操作を開始したときのポイントが,マークとして設定されます.

*6:OS (Windows)レベルでそのように変換している,と聞いたことがあります.実際,Firefoxのテキスト入力可能なところで,Altを押しながら@キーを押すと,英語・日本語の切替えになります.デメリットばかりでなく,これにより,「半角/全角 漢字」のない,英語キーボードでも日本語入力ができます.関連:英字配列キーボード: LocationsKnowledge

*7:実際には,改行コードがありますし,空白文字やタブが入っていても,他に文字がなければ空行となります.ですが,全角空白が入っている場合には,空行とみなされませんので,注意しましょう.

*8:バッファの先頭や末尾がマークとなることもあります.

*9:M-x helpのあと,vを押し,transient-mark-mode (Enter)とすると,この表現が見つかります.

*10:C-x 2として,同一バッファを複数のウィンドウで参照すれば,ポイントは別々につけられるのが分かります.