clang-format配置与使用

clang-format配置与使用

clang-format配置与使用

参考教程.

1. 安装

下载clang-format,设置环境变量。我使用的是vscode扩展中的clang-format。

位于: extensions/ms-vscode.cpptools-1.7.0-insiders/bin/。

将程序放置到系统边境变量的路径中,或者将软件路径添加到系统环境变量。

2. 配置

--style=指定配置文件。不指定将使用默认配置。默认情况下会先从当前目录寻找 .clang-format配置文件。这个配置有点弱智,难道就不能指定路径吗?

因此,自己定义的配置只能通过将.clang-format放置到需要格式化文件的路径下。因此,通过脚本或者程序的方式来复制配置文件到工作目录中。并在格式化完成后将其移除,这样可以不在工作目录下引入新的文件。

使用 Go来完成这个任务。(成功掌握可变参数和信道的使用-.-)

package main

import (

"fmt"

log "fmt"

"io"

"os"

"os/exec"

"path/filepath"

"runtime"

)

func main() {

clang_format_process(os.Args...)

}

func clang_format_process(args ...string) {

conf_dir, _ := filepath.Abs(filepath.Dir(os.Args[0]))

work_dir, _ := os.Getwd()

if conf_dir == work_dir {

if os := runtime.GOOS; os == "linux" {

conf_dir = filepath.Clean("/usr/local/sbin/clang_format_config.d")

} else if os == "windows" {

conf_dir = filepath.Clean("D:\\Program Files\\app")

}

}

work_dir_config := filepath.Join(work_dir, ".clang-format")

var config string = "config/.clang-format"

conf_dir_config := filepath.Join(conf_dir, filepath.Clean(config)) /* 使用clean生成与平台无关的路径 */

/* 根据不同的平台选择不同的格式化工具 */

var tool_dir string

switch os := runtime.GOOS; os {

case "windows":

tool_dir = filepath.Join(conf_dir, "bin/clang-format.exe")

case "linux":

tool_dir = filepath.Join(conf_dir, "bin/clang-format")

}

if _, err := os.Stat(tool_dir); err != nil {

log.Println("Error: no such file: ", tool_dir)

return

}

// is_custom := flag.Bool("nc", false, "custom argurement lists")

// flag.Parse()

if len(os.Args) <= 1 {

log.Println("Usage: \nclang_format_custom file.c file1.c\nor clang_format_custom -nc (= clang-format[.exe] )")

return

}

// 使用-cu参数,请删除true和修改os.Args[2:]

if os.Args[1] != "-nc" {

arg_pos := 1

print_args(os.Args[1:]...)

if _, err := os.Stat(work_dir_config); err == nil {

log.Println(work_dir_config)

log.Println(".clang-format has existed.")

return

}

/* 复制配置文件当工作目录中 */

if _, err := copy(conf_dir_config, work_dir_config); err != nil {

log.Println(err)

}

ch := make(chan int)

for _, arg := range os.Args[arg_pos:] {

go clang_format_exec(ch, tool_dir, work_dir, arg)

}

// 阻塞在此,等待所有goroutine完成

for i := arg_pos; i < len(os.Args); i++ {

<-ch

}

os.Remove(work_dir_config)

return

} else {

cmd := exec.Command(tool_dir, os.Args[2:]...) /* 不使用自定义参数时,直接调用clang-format */

output, err := cmd.CombinedOutput()

if err != nil {

log.Println(err)

}

fmt.Print(string(output))

return

}

}

func print_args(args ...string) {

log.Println("----------args list--------------")

for _, arg := range args {

log.Println(arg)

}

log.Println("-------------end-----------------")

}

func clang_format_exec(ch chan int, tool_dir, work_dir, file string) {

log.Println("format ", file)

cmd := exec.Command(tool_dir, "-i", file)

err := cmd.Run()

if err != nil {

log.Println(err)

}

ch <- 1

}

func copy(src, dst string) (int64, error) {

sourceFileStat, err := os.Stat(src)

if err != nil {

return 0, err

}

if !sourceFileStat.Mode().IsRegular() {

return 0, fmt.Errorf("%s is not a regular file", src)

}

source, err := os.Open(src)

if err != nil {

return 0, err

}

defer source.Close()

destination, err := os.Create(dst)

if err != nil {

return 0, err

}

defer destination.Close()

nBytes, err := io.Copy(destination, source)

return nBytes, err

}

程序目录结构:

.

├── bin

│ ├── clang-format

│ └── clang-format.exe

├── clang_format_custom

├── clang_format_custom.exe

├── config

├── .clang-format

└── .clang-format_backup

执行结果:

好了,宏定义对齐终于酸爽了。根据自己的喜好配置.clang-format配置文件。我的配置如下:

---

Language: Cpp

# BasedOnStyle: LLVM

AccessModifierOffset: -4

AlignAfterOpenBracket: Align

AlignConsecutiveMacros: true

AlignConsecutiveAssignments: true

AlignConsecutiveBitFields: true

AlignConsecutiveDeclarations: true

AlignEscapedNewlines: Right

AlignOperands: Align

AlignTrailingComments: true

AllowAllArgumentsOnNextLine: true

AllowAllConstructorInitializersOnNextLine: true

AllowAllParametersOfDeclarationOnNextLine: true

AllowShortEnumsOnASingleLine: true

AllowShortBlocksOnASingleLine: Never

AllowShortCaseLabelsOnASingleLine: false

AllowShortFunctionsOnASingleLine: false

AllowShortLambdasOnASingleLine: All

AllowShortIfStatementsOnASingleLine: Never

AllowShortLoopsOnASingleLine: false

AlwaysBreakAfterDefinitionReturnType: None

AlwaysBreakAfterReturnType: None

AlwaysBreakBeforeMultilineStrings: false

AlwaysBreakTemplateDeclarations: MultiLine

BinPackArguments: true

BinPackParameters: true

BraceWrapping:

AfterCaseLabel: false

AfterClass: false

AfterControlStatement: Never

AfterEnum: false

AfterFunction: false

AfterNamespace: false

AfterObjCDeclaration: false

AfterStruct: false

AfterUnion: false

AfterExternBlock: false

BeforeCatch: false

BeforeElse: false

BeforeLambdaBody: false

BeforeWhile: false

IndentBraces: false

SplitEmptyFunction: true

SplitEmptyRecord: true

SplitEmptyNamespace: true

BreakBeforeBinaryOperators: None

BreakBeforeBraces: Allman

BreakBeforeInheritanceComma: false

BreakInheritanceList: BeforeColon

BreakBeforeTernaryOperators: true

BreakConstructorInitializersBeforeComma: false

BreakConstructorInitializers: BeforeColon

BreakAfterJavaFieldAnnotations: false

BreakStringLiterals: true

ColumnLimit: 120

CommentPragmas: '^ IWYU pragma:'

CompactNamespaces: false

ConstructorInitializerAllOnOneLineOrOnePerLine: false

ConstructorInitializerIndentWidth: 4

ContinuationIndentWidth: 4

Cpp11BracedListStyle: true

DeriveLineEnding: true

DerivePointerAlignment: false

DisableFormat: false

ExperimentalAutoDetectBinPacking: false

FixNamespaceComments: true

ForEachMacros:

- foreach

- Q_FOREACH

- BOOST_FOREACH

IncludeBlocks: Preserve

IncludeCategories:

- Regex: '^"(llvm|llvm-c|clang|clang-c)/'

Priority: 2

SortPriority: 0

- Regex: '^(<|"(gtest|gmock|isl|json)/)'

Priority: 3

SortPriority: 0

- Regex: '.*'

Priority: 1

SortPriority: 0

IncludeIsMainRegex: '(Test)?$'

IncludeIsMainSourceRegex: ''

IndentCaseLabels: false

IndentCaseBlocks: false

IndentGotoLabels: true

IndentPPDirectives: None

IndentExternBlock: AfterExternBlock

IndentWidth: 4

IndentWrappedFunctionNames: false

InsertTrailingCommas: None

JavaScriptQuotes: Leave

JavaScriptWrapImports: true

KeepEmptyLinesAtTheStartOfBlocks: true

MacroBlockBegin: ''

MacroBlockEnd: ''

MaxEmptyLinesToKeep: 1

NamespaceIndentation: None

ObjCBinPackProtocolList: Auto

ObjCBlockIndentWidth: 2

ObjCBreakBeforeNestedBlockParam: true

ObjCSpaceAfterProperty: false

ObjCSpaceBeforeProtocolList: true

PenaltyBreakAssignment: 2

PenaltyBreakBeforeFirstCallParameter: 19

PenaltyBreakComment: 300

PenaltyBreakFirstLessLess: 120

PenaltyBreakString: 1000

PenaltyBreakTemplateDeclaration: 10

PenaltyExcessCharacter: 1000000

PenaltyReturnTypeOnItsOwnLine: 60

PointerAlignment: Right

ReflowComments: true

SortIncludes: true

SortUsingDeclarations: true

SpaceAfterCStyleCast: false

SpaceAfterLogicalNot: false

SpaceAfterTemplateKeyword: true

SpaceBeforeAssignmentOperators: true

SpaceBeforeCpp11BracedList: false

SpaceBeforeCtorInitializerColon: true

SpaceBeforeInheritanceColon: true

SpaceBeforeParens: ControlStatements

SpaceBeforeRangeBasedForLoopColon: true

SpaceInEmptyBlock: false

SpaceInEmptyParentheses: false

SpacesBeforeTrailingComments: 1

SpacesInAngles: false

SpacesInConditionalStatement: false

SpacesInContainerLiterals: true

SpacesInCStyleCastParentheses: false

SpacesInParentheses: false

SpacesInSquareBrackets: false

SpaceBeforeSquareBrackets: false

Standard: Latest

StatementMacros:

- Q_UNUSED

- QT_REQUIRE_VERSION

TabWidth: 4

UseCRLF: false

UseTab: Never

WhitespaceSensitiveMacros:

- STRINGIZE

- PP_STRINGIZE

- BOOST_PP_STRINGIZE

...

🔍 相关推荐