我想过滤我正在Sublime Text 2中编辑的文件,因为行包含某个字符串,如果可能的话包括正则表达式。
考虑以下文件:
foo bar
baz
qux
quuux baz
过滤时 ba
,结果应该是:
foo bar
baz
quuux baz
我怎样才能做到这一点?
我想过滤我正在Sublime Text 2中编辑的文件,因为行包含某个字符串,如果可能的话包括正则表达式。
考虑以下文件:
foo bar
baz
qux
quuux baz
过滤时 ba
,结果应该是:
foo bar
baz
quuux baz
我怎样才能做到这一点?
Answers:
Sublime Text 2是一个带有的可扩展编辑器 Python API 。您可以创建新命令(称为 插件 )并从UI中获取它们。
在Sublime Text 2中,选择 工具»新插件 并输入以下文本:
import sublime, sublime_plugin
def filter(v, e, needle):
# get non-empty selections
regions = [s for s in v.sel() if not s.empty()]
# if there's no non-empty selection, filter the whole document
if len(regions) == 0:
regions = [ sublime.Region(0, v.size()) ]
for region in reversed(regions):
lines = v.split_by_newlines(region)
for line in reversed(lines):
if not needle in v.substr(line):
v.erase(e, v.full_line(line))
class FilterCommand(sublime_plugin.TextCommand):
def run(self, edit):
def done(needle):
e = self.view.begin_edit()
filter(self.view, e, needle)
self.view.end_edit(e)
cb = sublime.get_clipboard()
sublime.active_window().show_input_panel("Filter file for lines containing: ", cb, done, None, None)
另存为 filter.py
在 ~/Library/Application Support/Sublime Text 2/Packages/User
要将此插件添加到 编辑 菜单,选择 首选项...»浏览包 并打开 User
夹。如果一个文件叫 Main.sublime-menu
不存在,创造它。在该文件中添加或设置以下文本:
[
{
"id": "edit",
"children":
[
{"id": "wrap"},
{ "command": "filter" }
]
}
]
这将插入 filter
命令调用(基本上, filter
变成了 FilterCommand().run(…)
对于插件调用和 过滤 对于菜单标签)就在下方 wrap
命令。看到 这里是第11步 更详细的解释为什么会这样。
要分配键盘快捷键,请打开并编辑该文件 Default (OSX).sublime-keymap
在OS X上,或其他系统的等效项,并输入以下内容:
[
{
"keys": ["ctrl+shift+f"], "command": "filter"
}
]
这将分配快捷方式 ^ ⇧ F 这个命令。
使命令显示在 命令调色板 ,您需要创建一个名为的文件 Default.sublime-commands
(或编辑现有的) User
夹。语法类似于刚刚编辑的菜单文件:
[
{ "caption": "Filter Lines in File", "command": "filter" }
]
多个条目(用大括号括起来)需要用逗号分隔。
执行的命令将过滤作为选择的一部分的所有行(整行,而不仅仅是选定的部分),或者,如果不存在选择,则过滤整个缓冲区,用于输入到输入字段的子字符串(触发命令后,default是 - 可能无用的多行 - 剪贴板。它可以很容易地扩展到例如支持正则表达式,或只留下行 不 匹配某个表达式。
要添加对正则表达式的支持,请使用以下脚本和代码段:
filter.py
:
import sublime, sublime_plugin, re
def matches(needle, haystack, is_re):
if is_re:
return re.match(needle, haystack)
else:
return (needle in haystack)
def filter(v, e, needle, is_re = False):
# get non-empty selections
regions = [s for s in v.sel() if not s.empty()]
# if there's no non-empty selection, filter the whole document
if len(regions) == 0:
regions = [ sublime.Region(0, v.size()) ]
for region in reversed(regions):
lines = v.split_by_newlines(region)
for line in reversed(lines):
if not matches(needle, v.substr(line), is_re):
v.erase(e, v.full_line(line))
class FilterCommand(sublime_plugin.TextCommand):
def run(self, edit):
def done(needle):
e = self.view.begin_edit()
filter(self.view, e, needle)
self.view.end_edit(e)
cb = sublime.get_clipboard()
sublime.active_window().show_input_panel("Filter file for lines containing: ", cb, done, None, None)
class FilterUsingRegularExpressionCommand(sublime_plugin.TextCommand):
def run(self, edit):
def done(needle):
e = self.view.begin_edit()
filter(self.view, e, needle, True)
self.view.end_edit(e)
cb = sublime.get_clipboard()
sublime.active_window().show_input_panel("Filter file for lines matching: ", cb, done, None, None)
Main.sublime-menu
:
[
{
"id": "edit",
"children":
[
{"id": "wrap"},
{ "command": "filter" },
{ "command": "filter_using_regular_expression" }
]
}
]
Default (OSX).sublime-keymap
:
[
{
"keys": ["ctrl+shift+f"], "command": "filter"
},
{
"keys": ["ctrl+shift+option+f"], "command": "filter_using_regular_expression"
}
]
第二个插件命令, 使用正则表达式过滤 将在下面添加 过滤 菜单条目。
Default.sublime-commands
:
[
{ "caption": "Filter Lines in File", "command": "filter" },
{ "caption": "Filter Lines in File Using Regular Expression", "command": "filter_using_regular_expression" }
]
还有一个 穷人的线路过滤算法 (或者它是懒惰的?):
现在有一个 插入 过滤线: https://github.com/davidpeckham/FilterLines
它允许基于字符串或正则表达式进行过滤和代码折叠。
您可以使用Sublime的内置功能在3到7个击键中执行此操作(不包括要匹配的正则表达式)。
选项1:多选所有包含子字符串的行
选项2:多选选择与正则表达式匹配的所有行
选项1:摆脱所有线条 不是 选
选项2:摆脱所有线条 是 选
选项3:将选定的行提取到新文件