4. Mối liên quan giữa con trỏ, hàm, mảng, chuỗi và cấu trúc
4.4. Con trỏ và chuỗi ký tự
C quan niệm chuỗi ký tự là một mảng ký tự, nhưng con trỏ ký tự có hơi khác với mảng ký tự.
Ví dụ 17 : Khai báo:
char s[50]; // Hoặc char s[] = “ABCD”;
char *p; // Hoặc char *p = “ABCD”;
Phép gán :
s = “ABCD”; /* sai (s là một hằng địa chỉ̉), phải dù̀ng strcopy(s,”ABCD”)*/
p=”ABCD”; //đú́ng (p là một con trỏ)
Truy cập phần tử:
s[0]==’A’ tương đương *(p+0)==’A’
s[1]==’B’ tương đương *(p+1)==’B’
Đọc, viết chuỗi ký tự:
gets(s); tương đương gets(p); //đọc chuỗi ký tự từ bàn phím
puts(s); tương đương puts(p); //viết chuỗi ký tự ra màn hình
hoặc
printf(“%s”,s); tương đương printf(“%s”,p);
//viết chuỗi ký tự ra màn hình
Con trỏ và mảng chuỗi ký tự: C quan niệmmảng chuỗi ký tự là một
mảng 2 chiều có kiểu char, nhưng con trỏ chuỗi có hơi khác với mảng chuỗi.
Ví du 18:
Khai báo: Mảng ten có 5 phần tử, mỗi phần tử chứa tố đa 8 ký tự
mảng gồm 5 phầ̀n tử có́ độ dài tối đa là 8 ký tự
char ten[5][9];
/*hoặc char ten[5][9]= { "Minh", "Tuan", "Binh", "Nam", "Ngan" };*/ // mảng gồm 5 con trỏ có́ kiểu char
char * ds[5];
//Hoặc char *ds={ "Minh", "Tuan",
"Binh", "Nam", "Ngan" }; Phép gán:
Lưu ý: Khởi tạo mảng mà không dù̀ng con trỏ thì lượng ô nhớ cấp phát cho mỗi phầ̀n tử của mảng đều bằng với số ký tự của chuỗi dài nhất; Trong khi đó́, nếu khởi tạo bằng mảng con trỏ thì lượng ô nhớ sẽ cấp phát vừa đủ cho từng phầ̀n tử của mảng.
Truy cập tới phần tử mảng:
Ten[0]== "Minh" tương đương ds[0]=="Minh"
Ten[1]== "Tuan" tương đương ds[1]=="Tuan"
…
Ví dụ 19: Dùng mảng chuỗi ten chứa dữ liệu, cho mảng con trỏ p trỏ vào mảng chuỗi ten #include <stdio.h> #include <conio.h> #include <string.h> #include <stdlib.h> #include <alloc.h>
void NhapMchuoi( char xau[][10],char *p[], int n); void InMchuoi( char *p[], int n ); void SXMchuoi( char *p[], int n);
int Menu(); void main(void) { int n,chon; char ten[10][10]; char *p[10]; do { chon=Menu(); switch (chon) { case 1:
printf("\n nhap so luong ten <=10:"); scanf("%d",&n); NhapMchuoi(ten,p,n);
break; case 2:
InMchuoi(p,n); getch();
break; case 3:
SXMchuoi(p,n); break;
default: printf("\n Ban chon chua dung!"); }
} while (chon!=0); free(p); }
int Menu() { int chon; clrscr();
printf("\n MOT SO THUAT TOAN VE MANG CHUOI\n\n"); printf(" 1. Nhap ho ten\n"); printf(" 2. Hien danh sach ho ten\n"); printf(" 3. Sap xep ho ten\n");
printf(" 0. Thoat khoi chuong trinh\n");
printf(" Nhan so tuong ung de chon chuc nang:\n"); scanf("%d",&chon);
return (chon); }
void NhapMchuoi(char xau[][10],char *p[], int n) { int i; char x[10];
fflush (stdin);
for (i=0; i < n ; i++) {
printf("\n Nhap chuoi thu %d ",i); gets(xau[i]);p[i]=xau[i];
} }
void InMchuoi( char *p[], int n) {
int i;
puts(p[i]); }
void SXMchuoi( char *p[], int n) {int i, j; char
*tg;
for (i=0; i<n-1; i++) for (j=i+1; j<n; j++) if (stricmp (p[i],p[j]) >0) { tg=p[i]; p[i]=p[j]; p[j]=tg; } }
Ví dụ 20: Dùng mảng con trỏ chuỗi p để chứa xâu ký tự
/*thay hàm nhapMCTchuoi vào chương trinh trên và chạy thử, nhận xét kế́t quả̉*/
void NhapMCTchuoi(char *p[], int n) { char x[10];
int i;
fflush (stdin);
for (i=0; i < n ; i++)
{ p[i]=(char*)malloc(10 * sizeof(char));
printf("\n Nhap chuoi thu %d ",i); gets(x); strcpy(p[i],x);
}
} /*lưu ý dù̀ng hàm free(p) giải phó́ng bộ nhớ động trước khi kết thúc chương trình */