Using Clang-format to ensure clean, consistent code

428 readers like this. keynote address

Too often programmers underestimate the importance a consistent coding style can have on the success of a project. It makes the code base easier to read, reduces nonfunctional changes to fix inconsistent style, and outlines expectations for code submissions. Most large projects have a coding style, and once you have been working on code for a while you come to appreciate the consistency of a style. Some examples of specified style are where to place braces, whether tabs or spaces are used for indentation, how many spaces to indent by, and how to break up long lines.

Using Clang-format

Having a consistent coding style is important, but it can also be a pain to describe and takes time to go over in code reviews. Clang-format is one code formatting tool I have been tracking for quite some time now, along with several of its predecessors. This project reuses the language parser in clang, which means it has a solid model of the C++ programming language, and so it does not have to rely on regular expression matching as some other tools do.

# This configuration requires clang-format 3.8 or higher.
BasedOnStyle: Mozilla
AlwaysBreakAfterReturnType: None
AlwaysBreakAfterDefinitionReturnType: None
BreakConstructorInitializersBeforeComma: false

For Tomviz, 3D scientific data visualization software for tomographic data, I based our format file on what CMake, a tool for building and testing software, used in its recent conversion, with some minor adjustments. You can simply place a .clang-format file in the base source directory, and the tool will scan from the current directory and up until it encounters this file. I was then able to run it on all of our source files, and a colleague added an automated hook to our GitHub repository to validate whether or not proposed changes complied with the style file. All pull requests are now run through the checks, with the necessary changes supplied if the test fails. This removes the need to review pull requests for coding style, and ensures our code base has a uniform style. We have also extended this to our Python code using flake8, a style-guide enforcement tool.

Developers can apply the style to their changes easily. I usually run clang-format -i path/to/changed.*, and there are other ways to use the tool. Now to weigh in on the great brace placement war, but we have chosen to side with CMake and keep the brace on the same line as the statement, preserving maximum vertical space. The ParaView data analysis and visualization project just merged their clang-format changes, opting to place the braces on a new line. VTK (Visualization Toolkit, a 3D computer graphics, image processing, and visualization software) uses a custom script that also places them on a new line. They plan to migrate to clang-format.

Automating these specifics frees up development time while still fostering style uniformity. The clang-format tool enables us to express our code style in a very succinct fashion, and we can apply it easily before committing changes. Clang-format also understands and works well with diffs/git. I hope to take a look at clang-tidy soon because I am looking for a tool that automatically checks for some deeper C++ coding style issues, such as preferring new C++11 language features.

These tools make the creative process easier for new developers because they can simply run the tool to get most of the formatting right without having to read through lengthy coding style documentation for any given project. It also removes some of the edge cases that can get overlooked in reviews or result from different interpretations of the style guide. These tools are quite language specific, but I would encourage you to consider employing them (or equivalents where available) in your development workflow.

In closing

Never use tabs, always spaces. Vim is of course the one true text editor. And dogs are superior to cats as household pets.

Marcus D. Hanwell
Marcus D. Hanwell | Marcus leads the Open Chemistry project, developing open source tools for chemistry, bioinformatics, and materials science research.


As proof of "In Closing" --

% man dog
DOG(1) User Manuals DOG(1)

dog - better than cat

dog [-AbBeEnstTuv] [-w cols] [-l lines] [--show-all] [--number-nonblank]
[--no-blanks] [--bind=port] [--dos] [--show-ends] [--hang-up] [--images]
[--krad] [--links] [--lower] [--mac] [--number] [--no-header] [--squeeze-blank]
[--strfry] [--sock=domain:port] [--sock-test] [--show-tabs] [--raw] [--rot=num]
[--udp] [--unix] [--upper] [--show-nonprinting] [--hide-nonprinting] [--help]
[--hex] [--skip-tags] [--oog] [--version] file | URL | -

dog writes the contents of each given file, URL, or the standard input if none
are given or when a file named '-' is given, to the standard output. It cur-
rently supports the file, http, and raw URL types. It is designed as a compati-
ble, but enhanced, replacement of cat(1).

That is really cool, I haven't come across dog before, thanks for the supporting evidence!

In reply to by Carlie Coats (not verified)

"Never use tabs, always spaces. Vim is of course the one true text editor. And dogs are superior to cats as household pets."

You had to blow it with your last two sentences, alas. I was with you up until then.

I am glad I had you up until there, I wanted to throw in a little controversy at the end and see how heated we could get the debate ;-)

In reply to by dgrb (not verified)

Thank you for the article. I didn't know the flake8 tool.

Creative Commons LicenseThis work is licensed under a Creative Commons Attribution 4.0 International License.