プログラミングC: 投稿 11 – C言語でポインタ

1. Cでの紹介ポインタ

私たちは、過去に知られており、使用している変数は、サイズと識別データ型で可変です. 彼らは、このタイプの変数は静的変数である呼び出す. あなたは静的変数を宣言すると, 可変量のメモリセルは、そのメモリセルの全てかを使用して、プログラム実行中に知ることなく配分される. 一方, 静的変数のこの形式は、プログラムのみを使用して変化にもかかわらず、プログラムの実行中に存在します 1 使い捨て.

静的変数を使用する際にいくつかの制限が発生する可能性がある:

  • メモリセルバランスを割り当て, 無駄なメモリセルを引き起こす.
  • 不足しているメモリセルを割り当て, プログラム実行エラー.

制限を上避けるために、, C言語は、次の特性を持つ特殊変数と呼ばれるボラティリティを提供してくれます:

  • 唯一の起動プログラムで発生するしない、プログラムの実行中に発生する.
  • プログラムを実行しているとき, 変数のサイズ, メモリとメモリアドレスが変更されることがあり、変数に割り当てられる.
  • あなたが使用して終了したら、それは遊離は、メモリ内のスペースを節約することができます. ただし、特定の対処していない変化が私はそれらにアクセスすることができません. 従って, C言語では、これを克服するために、再度変数の特別な種類を提供してくれます, あるポインタ変数 (ポインタ) 特性を持つ:
  • ポインタ変数は、データのアドレスが含まれているデータが含まれているか、データを含むメモリのアドレスが含まれていない.
  • ポインタのサイズは、データの種類に依存しない.

2. ポインター

各変数はに割り当てられていると宣言される 1 特定のメモリ領域どこ (アドレス) 異なる. ポインター 変数 変数のアドレスを格納するために使用.

2.1 例

// e.g about pointer - code by nguyenvanquan7826
#include <stdio.h>

int main() 
{
    /* khai bao bien x va bien con tro px */
    int x, *px; 
    px = &x;
    /* &x : tra ve dia chi cua bien x
     * px = &x : gan dia chi cua bien x cho px hay px tro den x
     */

    x = 42;

    printf("Vi tri cua bien x la %p \n", &x);
    printf("Noi dung cua bien x la %d \n", x);
    printf("Vi tri cua bien x la %p \n", px);
    printf("Noi dung cua bien x la %d \n", *px);

    *px = 7826;
    printf("\n -------- \n\n");

    printf("Noi dung cua bien x la %d \n", x);
    printf("Noi dung cua bien x la %d \n", *px);

    return 0;
}

結果:

結果:
ラX記録 42
viのトライCUAもX 0x7ffe064348fc
ラX記録 42

--------
ラX記録 7826
ラX記録 7826

このオープニング例を通して、私たちは、以下の点を描くことができます:

ザ·. カーソル変数を宣言

データの種類ごとに、我々はそれぞれ、その型のポインタ変数を持つ.

タイプ * 名前ポインタ;

上記の例では、宣言 1 int型PXのポインタ変数.

B. を指し示すポインタの規制

私たちは、演算子を使用 & アドレス用 1 変数とそのアドレスポインタを割り当てる.
=ポインタに名前を付け &変数;

℃. アクセス方法

カーソルPXして上に持っている 2 許可証はあるが:

  • PX : それが保たれるアドレスを取得します (ポイントへ)
  • *PX : それが指すメモリの値を取得.

上の例では、代入後にそれを見ることができます PX = &x; その後、我々は書く:

  • PXはに相当します &X
  • *PXはXに相当します. および計算の*のピクセルに使用することができる, 表現.

D. ポインタ上のいくつかの操作

// e.g about pointer - code by nguyenvanquan7826
#include <stdio.h>

int main() 
{
    /* khai bao bien x va 2 bien con tro px, qx */
    int x, *px, *qx; 
    px = &x;

    printf("Nhap gia tri cho vung nho px tro toi: ");
    scanf("%d", px); 
    /* px la con tro nen khong viet scanf("%d", &px);  */

    qx = px; /* gan gia tri cua px cho qx, qx cun tro toi x*/

    printf("Vi tri cua bien x la %p \n", &x);
    printf("Vi tri cua bien x la %p \n", px);
    printf("Vi tri cua bien x la %p \n", qx);
    printf("Noi dung cua bien x la %d \n", x);
    printf("Noi dung cua bien x la %d \n", *px);
    printf("Noi dung cua bien x la %d \n", *qx);

    // tang gia tri cua o nho len, <=> x = x + 7826
    *px += 7826; 
    printf("Noi dung cua bien x la %d \n", x);

    px++; 
    /* cong them mot don vi cho px
     *  => px tro toi vung nho tiep theo
     */

    printf("Vi tri px tro toi la %p \n", px);

    return 0;
}

結果:

入り江のPX灰TOIの値を入力します: 42
ViにトライよくCUA X 0xbfba58a0
ViにトライよくCUA X 0xbfba58a0
ViにトライよくCUA X 0xbfba58a0
ラX記録 42
ラX記録 42
ラX記録 42
ラX記録 7868
ビトロソートのPXあなたの0xbfba58a4

例えばのために我々は後に共通のポインタに対していくつかの操作で見た: (多くの他の操作に加えて、).

  • 2 同じ型のポインタ変数は、相互に割り当てられているか、整数のために公共の会計処理を行うことができます, マイナス 2 それぞれのポインタ. 上記の例では、計算を実行する:
  • 近くに: Q X = PX; それを受信したときのピクセルのqxの値は、変数xのアドレスである, すなわちpxとQXとXを指している. さらに、我々は以下を割り当てることができます: Q X = PX + 2; QXと, PXは同じポインタ型です. 引き算 2 同じ型のポインタが返されます 1 整数値 (int型). これは距離であり、 (いくつかの要素) 間に 2 ポインタを含む
  • 増加する: 増加または減少を許可, 減算は同じポインタ演算変数で実行され. 唯一の違いは、それが上下することである, プラスまたはマイナスそれが有する単一バイトの種類に応じて.
    最高経営責任者(CEO. 上記の例では、増加させることが可能である: PX ; と仮定した場合、このアドレスPXを指している: 0xbfba58a0、その値が増加することができ (場所へのポイント) 0xbfba58a4 (増加する 4) PXはあるので、そのint型のint型のアカウントの各ポインタ変数 4 メモリ内のバイト.
  • さらに、我々は*のPX 数学によって、変数xの値を変更することが許可されている= 3; 本質的には、この操作は、メモリ内の値を変更した (アドレス) そのPXポイントへ, 変数xの値をもたらしたに応じて変更される.

あなたが気づいたことがあります:

  • コンパイラや、異なる種類の容量であるオペレーティングシステムに応じて、. (これはint型アカウントの翻訳です 4 バイトが、それが占有している他のサービスで 2 バイト). ストレージのタイプごとに、あなたは、sizeof演算子を使う() しかし、すべてで 2 言及.
  • また、オペレーティング・システムの各ポインタ変数に依存, カーソルの関係なく、どのタイプ (int型, フロート, ダブル,...) また、同じバイト数を占めています. オペレーティング·システム 32 ポインタ変数経理ビット 4 バイト, OS 64 ポインタ変数経理ビット 8 バイト.

3. 割り当て、メモリを回復

ザ·. 割り当て:

この1小さな例に先立ち.

// e.g about pointer - code by nguyenvanquan7826
#include <stdio.h>

int main() 
{
    int *px;
    *px = 42;
    printf("Vi tri con tro px la %p \n", px);
    printf("Gia tri con tro px tro toi la %d \n", *px);
    return 0;
}

コンパイルされたとき、それはメリットはありません (警告), ランはそのプログラムを実行することはできませんときバックアウトします.
その理由は、カーソル変数の宣言は、新しいマシンをPX場合にのみ提供するということです 2 ポインタデータ格納PXにメモリを割り当てるしていないポインタ変数のアドレスを格納するバイト. (同じような協力的な供給 2 あなたが同じことをするが、あなたのリングをメッキあなたに土地を与えないために米のキロ ).

注意: そこにコンパイラエラーの数がありますが、まだ正常に実行されませんが、最高のは、私たちが使用を割り当てるべきであるということです. あなたは私たちが、後で議論する配列へのポインタを使用する場合に、このエラーが最も明確に表示されます.

まあ我々は重要な問題に行きました, ポインタにメモリを割り当てる方法.
私たちは図書館stdlib.hで次の関数を使用ポインタにメモリを割り当てるために、.

  • のmalloc : 名前をカーソル= (ポインター型 *) のmalloc (はsizeof(ポインター型));
  • のcalloc : 名前をカーソル= (ポインター型 *) のmalloc (N, はsizeof(ポインター型));

そのはsizeofで(ポインター型) 型のサイズ; nはsizeof演算子の数であり、(ポインター型) 付与された.

// e.g about pointer - code by nguyenvanquan7826
#include <stdio.h>
#include <stdlib.h>

int main() 
{
    int *px, *qx;
    px = (int *) malloc(sizeof(int));
    qx = (int *) calloc(1, sizeof(int));

    printf("Vi tri con tro px la %p \n", px);
    printf("Gia tri con tro px tro toi la %d \n", *px);

    printf("Vi tri con tro qx la %p \n", qx);
    printf("Gia tri con tro qx tro toi la %d \n", *qx);
    return 0;
}

ここでは、注意してください: mallocとmalloc関数で割り当てられたときには、単に理解はcallocの唯一の違いは、機械PXを割り当て 1 どのようなデータで知ることなく、任意の細胞またはデータなしに細胞 (*上記のように貴重なPX) あまりにはcalloc、だけでなく、他の 1 マシンは自動的に常に値を割り当てます後にポイントが割り当てられている 0 変数のqx指すメモリセル, ニュースQXのデフォルト値です 0.
ポインタを割り当てるとき 1 我々は欠けなどを割り当てる必要がある作業工程中のメモリセルの一定量は、コマンドを使用し reallocを:

名前をカーソル= (ポインター型 *) reallocを (カーソル名, に割り当てられた量 * はsizeof(ポインター型));

その中で: 古いに割り当てられた=金額 + 招待する.
最高経営責任者(CEO: 当初我々は、ポインタがPXで割り当てられた 10 メモリセル.
その後、多くを割り当てるしたい 5 複数のメモリセルが、量が割り当て= 15.

B. 回復は、残りのメモリを確認

我々が使用するメモリ割り当て関数を回復するには 無料で(カーソル名);

3. カーソルの機能

すべてのように Cでの置換関数 我々は、パラメータAを渡す方法を知っている,HoanVi機能におけるbはアドレスではない送信により、値渡しされる (またはパラメータ) 従って、関数の変数の値が変更されたが、機能が実行された後、値は、まだ変更するいても. そして、我々は渡すパラメータにより改訂されるスワップにカーソルポインタbは、そのメモリセルのアドレスに交換することができる形式. そして、我々は望ましい結果を取得するとき.

// e.g about pointer - code by nguyenvanquan7826
#include <stdio.h>

void hoanVi(int *a, int *b) 
{
     int temp = *a;
     *a = *b;
     *b = temp;
}

int main() 
{
    int a = 42, b = 7826;
    printf("Truoc khi goi ham hoan vi: a = %d, b = %d \n", a, b);

    hoanVi(&a, &b);

    printf("Sau khi goi ham hoan vi: a = %d, b = %d \n", a, b);

    return 0;
}