How to write perfect C code

  Several days ago, I was involved in an argument about choice of C or C++. What I ignored was "language is less important than coder".  a bad C# writer only write shit-like C# but a professional C programmer could design perfect C, Notwithstanding C# is much more powerful than C,
  So how to write perfect C code? We just illustrate that by cJson, a famous pure-C tiny json formatter.

1. Power C pointer, make point operation awesome

The string-comparison of cjson like melody,  this ability might need you a lot experience:

    static int cJSON_strcasecmp(const char *s1,const char *s2)
    {
    if (!s1) return (s1==s2)?0:1;
    if (!s2) return 1;
    for(; tolower(*s1) == tolower(*s2); ++s1, ++s2)
        if(*s1 == 0)    return 0;
    return tolower(*(const unsigned char *)s1) - tolower(*(const unsigned char *)s2);
         }    

  So how you write a same strcasecmp function? Try more C code.

2. Reasonable code indent

   Someone might tell you write code with same indent-style, "the wrap position, where to put a bracket..." However, most people are accustomed to reading left to right without pause. So a better code reader understand is more important than that so-call rule and style just like follows:

static const char *parse_value(cJSON *item,const char *value)
{
    if (!value)                        return 0;    /* Fail on null. */
    if (!strncmp(value,"null",4))    { item->type=cJSON_NULL;  return value+4; }
    if (!strncmp(value,"false",5))    { item->type=cJSON_False; return value+5; }
    if (!strncmp(value,"true",4))    { item->type=cJSON_True; item->valueint=1;    return value+4; }
    if (*value==‘\"‘)                { return parse_string(item,value); }
    if (*value==‘-‘ || (*value>=‘0‘ && *value<=‘9‘))    { return parse_number(item,value); }
    if (*value==‘[‘)                { return parse_array(item,value); }
    if (*value==‘{‘)                { return parse_object(item,value); }

    ep=value;return 0;    /* failure. */
}

  Does Code below make it more easy to understand than standard indent style? As you can easily compare difference between each case of switch structure.

3. Chain-style function design

  Chain-style function means you can invoke them with merge them into a chain, as A(B(C)).
 
 Linq (a chain-style code sugar ) greatly improve beauty of C#, could
make your code designed like: Select.Where.Orderby...  As standard C do
not offer extend-function. But you could still make the chain like
Order(Select(Where(Data))) .  Some little bit harder ,but much more
easier than other code style, just like code in cJson:

   value=skip(parse_value(child,skip(value+1)));    /* skip any spacing, get the value. *

The difficulty is the rope which connect modules into a chain. In
Linq, it‘s a interface called IEnumerable, a compiler-level state
machine. In cJson code behind, it‘s the position of processing pointer.

4. Hook me!

 
 Standard C do not have delegate, function override. But there are some
other powerful mechanism called hook, achieved by function pointer. You
could change a function pointer behaviour by assign a different function
with same parameters and return value. Example as follow:

    void cJSON_InitHooks(cJSON_Hooks* hooks)
{
    if (!hooks) { /* Reset hooks */
        cJSON_malloc = malloc;
        cJSON_free = free;
        return;
    }

    cJSON_malloc = (hooks->malloc_fn)?hooks->malloc_fn:malloc;
    cJSON_free     = (hooks->free_fn)?hooks->free_fn:free;
}

Awesome right? You can change memory allocation and free behaviour by using hook!

5. Offer default value of function parameters

   In order to make your user more convenient when using your perfect library, please offer them some override functions! C might not allow you define two same name function by different parameter table. But you could still do this:

/* Render a cJSON item/entity/structure to text. */
char *cJSON_Print(cJSON *item)                {return print_value(item,0,1);}
char *cJSON_PrintUnformatted(cJSON *item)    {return print_value(item,0,0);}

6. Improve algorithm!

   C style code is different than C# or Java, the languages with powerful libraries. Sometimes because of compatibility or performance, using STL or some 3rd libraries is not a good choice. So you need to achieved them by yourself. This does not means you should write "Stack.c" or  "Stack.h"  to define a full-functional stack. It‘s too heavy and unnecessary,right? But the core algorithm of stack will greatly affect your code style by merge an easy array-achieved stack by several simple code.
    The example in cJson is tree structure, as json is a
nature tree. The author merge tree algorithm into the code by recursive
and pointer without any trace. Perfect!
    
    Try more C code, try more perfect improvement, guy!

时间: 2024-10-08 10:26:03

How to write perfect C code的相关文章

Project Perfect让Swift在server端跑起来-Perfect in Visual Studio Code (四)

编者语 : 本系列文章已经被Perfect官方引用了,这样的感觉非常好.感恩!Thx all ! Visual Studio Code是一个轻量级的编辑器,但也功能丰富,通过插件你能够完毕如Cordova,ReactNative,NodeJS,PHP,ASP.NET Core 的开发.上文通过Visual Studio Code对Perfect文件进行编辑,但编译过程还是在终端中完毕. 事实上通过对Visual Studio Code 加入tasks.json就能够完毕对Perfect项目的编译

一、Perfect Squares 完全平方数

h3 { background-color: palegreen } 一原题 Given a positive integer n, find the least number of perfect square numbers (for example, 1, 4, 9, 16, ...) which sum to n. For example, given n = 12, return 3 because 12 = 4 + 4 + 4; given n = 13, return 2 beca

LeetCode 279. Perfect Squares

Question: Given a positive integer n, find the least number of perfect square numbers (for example, 1, 4, 9, 16, ...) which sum to n. For example, given n = 12, return 3 because 12 = 4 + 4 + 4; given n = 13, return 2 because 13 = 4 + 9. Code: public

如何在python脚本开发做code review

在软件项目开发中,我们经常提到一个词"code review".code review中文翻译过来就是代码评审或复查,简而言之就是编码完成后由其他人通过阅读代码来检查代码的质量(可编译.可运行.可读.可维护.可复用),这些性质都比较抽象,但是一般都可以通过以下的检查点来实现: 检查代码的命名方式是否符合规范,代码的可读和可维护必须要求所有参与编码的同事使用的命名有统一的规范(注意每个人有自己的代码风格,但是要符合可读性的代码规范): 检查代码的注释,注释一般包括:1.类要有类用途和使用

Java Code Style 记录

示例代码: 1 class Solution { 2 /** 3 * @param nums: A list of integers. 4 * @return: A list of unique permutations. 5 */ 6 public List<List<Integer>> permuteUnique(int[] nums) { 7 // Write your code here 8 ArrayList<List<Integer>> rst

Perfect smooth scrolling in UITableViews

https://medium.com/ios-os-x-development/perfect-smooth-scrolling-in-uitableviews-fd609d5275a5 Difficulty and the depth of material will increase from the beginning to the end of story, so I’ll start with things which are familiar to many of you. Deep

POJ 1543 Perfect Cubes

Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 14344   Accepted: 7524 Description For hundreds of years Fermat's Last Theorem, which stated simply that for n > 2 there exist no integers a, b, c > 1 such that a^n = b^n + c^n, has remain

[读后感]从Code Review 谈如何做技术

还有9个电,争取把这篇发出去,里面有太同共鸣,只不过之前没能写出来, 一是文笔有限,总结不够明确,本文至少总结出了我想总结的6个观点,看来总结能力还是要提高: 二是不确认这是对的,所以不敢贸然写出来,看来奔四的程序员都有这些共同的想法,并非我一人,还有许多人... 着实说,代码审查,以前想过,但没做过: 代码审查确实很不错,不懂开发的测试人员其实从某种角度是用于粗暴地替代代码审查, 结果可知,花在修复 Bug 上的时间要比编码时间多 N 倍, 我想我们以敏捷方式来对付它,逐层皮儿地扒着做,做完一

Code Complete阅读笔记(二)

2015-03-06   328   Unusual Data Types    ——You can carry this technique to extremes,putting all the variables in your program into one big,juicy variable and then passingit everywhere.Careful programmers avoid bundling data any more than is logically