0

次の関数の簡単な C コードを作成しようとしています。

文字 ad のエンコーディングが与えられた場合:

'a'->00、'b'->01、'c'->10、'd'->11、

および次のように定義されたリンク リスト内のノード:

typedef struct listNode{
 unsigned char data;
 struct listNode* next;
}ListNode;

typedef struct list{
  ListNode* head;
  ListNode* tail;
}List;

whereheadはリストの最初のノードを指し、tailは最後のノードを指します。

char* SumList(List arr[], int n)arr 内のすべてのリストのすべてのノードにすべてのエンコードされた文字を含む文字列を返す関数を記述する必要があります。

これは私がこれまでに書いたものです:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

int isBitISet(char, int);

typedef struct listNode {
    unsigned char data;
    struct listNode* next;
} ListNode;

typedef struct list {
    ListNode* head;
    ListNode* tail;
} List;

int isBitISet(char ch, int i) {

    char mask;
    mask=1<<i;
    return (mask & ch);
}

int totalNodes(List arr[], int n) {
    int i;
    int counter=0;

    for (i=0; i<n; ++i) {
        ListNode* head= arr[i].head;
        while (head!=NULL) {
            counter++;
            head=head->next;
        }
    }
    return counter;
}

char* whatToadd(char data) {
    int a, b;
    a=isBitISet(data, 0);
    b=isBitISet(data, 1);
    char* result;
    result=(char *) calloc(2, sizeof(char));
    if ((a!=0) && (b!=0))
        result="d";
    else if ((a!=0) && (b==0))
        result="b";
    else if ((a==0) && (b!=0))
        result="c";
    else
        result="a";
    return result;

}

char* SumLists(List arr[], int n) {

    char* final;
    int nodes=totalNodes(arr, n);
    final= (char*) calloc(nodes, sizeof(char)); //how would I know the final length?//
    int i;

    for (i=0; i<n; ++i) {
        ListNode* head= (arr[i].head);
        while (head!=NULL) { //Why do I need a tail?//
            char* result;
            result=whatToadd(((head->data)&(00000011)));
            strcat(final, result);
            free(result);
            result=whatToadd(((head->data)&(00001100))>>2);
            strcat(final, result);
            free(result);
            result =whatToadd(((head->data)&(00110000))>>4);
            strcat(final,result);
            free(result);
            result=whatToadd(((head->data)&(11000000))>>6);
            strcat(final,result);
            free(result);

            head=head->next;

        }
    }
    return final;
}

int main() {
    .....

    free(final);
    ...
}

おそらく、テールは何らかの理由で与えたのでしょう-しかし(1) -私がしたようにリストを実行することはできませんか? しっぽを使わずに?そうでない場合は、どのように使用すればよいですか?

(2) - から新しい結果を取得するたびに行った方法で、結果を解放する必要がありwhatToAddますか?

私は C の初心者で、自分で作業しようとしています。ヒントや修正を実際に適用したいと思います。どうもありがとう。

4

1 に答える 1

1

whatToAddから新しい結果を取得するたびに、結果を解放する必要がありますか?

いいえ、文字列リテラルのアドレスが返されているためです。calloc()不要なので覚えないでくださいresult。文字列リテラルは読み取り専用であるため、whatToadd()の戻り値をに変更します。const char*

明確にするために、以下はにコピー"d"されませんresult

result="d";

しかし、代わりresultに文字列リテラルのアドレスを指し示します"a"。これはポインタの割り当てです。にコピーしたい場合resultは、次のいずれかを実行できます。

  • strcpy(result, "d");
  • *result = 'd'; *(result + 1) = 0;

その場合free()、返されたポインタになります。

free()への以前の呼び出しの結果である場合calloc()malloc()またはrealloc()まだfree()dになっていない場合にのみ、ポインタを渡します。

于 2012-07-17T09:44:58.437 に答える