2013-02-02 9 views
6

私はchar*を使用するが、バイト配列を期待する私のすべての関数は、char*を使用して、引数として文字列を期待する多くの関数を持っています。文字列とバイト配列を区別しますか?

問題は、ヌルターミネータが見つからないため、すべての種類のオーバーフローを引き起こす文字列関数でバイト配列を渡すのが間違っている可能性があることです。

これは通常どのようにデルタですか?私はuint8_tを取るためにすべての私のバイト配列関数を変更することを想像することができますし、コンパイラは文字列を渡すときに署名付きについて警告します。またはここに正しいアプローチは何ですか?

+0

バイト配列のラッパーを作成しますか? –

+0

@ VaughanHilts私の問題を解決する方法は見当たりませんか? – Muis

+0

文字列*はバイト配列です。実際にはCで配列を渡すことはできませんが、最初の要素へのポインタだけを渡すので、通常はサイズを渡す必要もあります。配列にゼロ値が含まれているかどうかを確認するだけです。そうであれば、それは "文字列"です。それ以外の場合は、そうではありません。 –

答えて

1

の... strncpystrncatstrncmpを使用することを意味します。 char*char[]関数パラメータに等価であるので、このようなパラメータは、3つの異なる意味論的概念を指すことができる。

  • 1つのcharオブジェクト上のポインタ(これはポインタ型の「公式」の定義である)
  • char C標準でmondernインターフェイスは型なしバイトARためvoid*を使用可能である多くの場合、アレイ
  • ストリング

あなたはその慣習に従うべきであり、文字列にはchar*を使用してください。

char[]それ自体はおそらくそれほど使用されません。私はこれらのユースケースをたくさん想像することはできません。それらを数字と考える場合は、というビットパターンを選択するのと同じように、signedまたはunsignedのバリアントを使用する必要があります。

あなたが本当に関数のパラメータとして配列を意味する場合(charか)あなたははっきりそれを示すことによって、あなたのコードのカジュアルな読者のためにその事実をマークすることができます

void toto(size_t n, char A[const n]); 

これは

void toto(size_t n, char *const A); 
に相当します

あなたの意図をより明確にします。そして、将来、あなたのためにチェックを行うツールがあるかもしれません。

2

私は一般的に次の

typedef struct { 
    unsigned char* data; 
    unsigned long length; 
    unsigned long max_length; 
} array_t; 

ような配列の何かが、その後など

+1

は、 'unsigned long'の代わりに' size_t'を使うほうがよいでしょう –

+0

あなたは正しい –

0

書き込み*

void array_create(array_t* a, unsgined long length) // allocates memory, sets the max_length, zero length 

void array_add(array_t* a, unsigned char byte) // add a byte 

を*周り

をarray_t渡し、array_t取る配列関数を作成します文字列とバイトの両方を扱う共通の構造体。

struct str_or_byte 
{ 
    int type; 
    union 
    { 
     char *buf; 
     char *str; 
    }pointer; 
    int buf_length; 
} 

typeが文字列でない場合のみbuf_length件までpointer.bufにアクセスします。そうでない場合は、buf_lengthをチェックせずに直接pointer.strにアクセスし、ヌル終了文字列としてそれを維持してください。

それ以外の場合は、長さだけを考慮して文字列をバイト配列としても維持してください。文字列にnull終了文字を保持しないでください。

struct str_or_byte 
{ 
    char *buf; 
    int buf_length; 
} 

長さを考慮していない文字列操作関数を使用しないでください。これは、問題はあなたが考えているよりも、Cでより一般的である代わりにstrcpystrcatstrcmp ...

0

Cを使用しています。ここに私が使用する規則があります(標準ライブラリの後に作成されます)

void foo(char* a_string); 

void bar(void* a_byte_array, size_t number_of_bytes_in_the_array); 

これは覚えやすいです。あなたが単一のchar * ptrを渡しているなら、それはヌル終端のchar配列でなければなりません。

関連する問題