vim可以自动重构这个代码片段吗?那是什么宏?

时间:2011-10-26 20:47:41

标签: vim

我的代码块看起来像:

ICar car = new Car<int>(10);
var result = car.Start(100);

Assert.IsTrue(result.IsValid);

我想转换成这个:

Assert.IsTrue((new Car<int>(10).Start(100)).IsValid);

我有大约20种这些类型的片段具有完全相同的格式,这可以在vim中自动化吗?

3 个答案:

答案 0 :(得分:4)

宏中的崩溃课程:

  • 以正常模式进入ICar。
  • 按qq启动宏。
  • 修改代码。尝试使用基于单词的动作而不是左/右箭头。
  • 转到下一个代码段,与/ ICar一样。
  • 在正常模式下再次按q可停止录制。

然后,您可以键入@q以执行q宏并重新格式化一个片段。如果它按预期工作,则输入20 @ q执行20次。

答案 1 :(得分:3)

:%s:^.* = \([^;]\+\);\_.[^.]\+\([^;]\+\);\n\n\+\([^(]\+\)(.*\.\(.*$\):\3((\1\2).\4

使用完全相同的格式(.=的位置等在原始模式中很重要。

HTH

答案 2 :(得分:3)

宏是最简单的,但另一种方法是使用全局命令 - :g/ 正则表达式 / Ex命令。例如(不是您的示例 - 我们稍后会介绍),您可以使用:g/^\s*ICar/delete删除以ICar开头的所有行(^用于开始行\s*用于跳过用于缩进的制表符和空格。)

此方法优于宏的优点是您可以在范围内使用它:进入可视模式,标记要重构的部分,并使用全局命令。只有标记块中的匹配才会受到影响。如果您使用宏,则需要反复按@@直到清除块,计算您希望宏运行的确切次数,或者设置一个较大的数字并进行不匹配错误停止宏。虽然第三个选项很容易执行,但它也非常危险 - 您需要确保模式在要重构的部分中仅显示 - 因此它不会影响代码的不相关部分 - 并且重构将其删除 - 否则宏将一遍又一遍地在同一行上运行。

宏的优点是它们更容易记录。在像您这样的复杂重构中,您需要运行的全局命令可能非常长且复杂。执行相同操作的宏与全局命令一样长且复杂 - 但是您可以在记录它时看到它的工作原理 - 比在设计全局命令时计算结果更容易。

幸运的是,你可以享受这两个世界!
首先,你记录你的答案中解释的像cdleonard这样的宏,主要有两点不同 第一个是宏中的第一个键击应该是^_ - 转到行中的第一个非空白字符(这意味着你从qq_开始然后像往常一样记录)。这将保证宏每次都从行中的正确位置开始 第二个区别是你不需要在宏的末尾转到下一个片段。全局命令将为您处理。

录制宏后(我假设您将其录制到q)使用可视模式标记所有片段,然后键入:g/^\s*ICar/norm @q - 这将搜索所有行的标记范围以ICar开头(可能在它们之前有缩进)并对它们执行宏。这假设范围内以ICar开头的所有内容 - 只有那些地方 - 是您要重构的片段。如果你的行以ICar开头并且你不想重构,或者你有想要应用宏的行,但它们不是以ICar开头 - 你将不得不修改正则表达式。