目次
1. はじめに
アドレス帳は皆さんよくご存知だと思いますが、アドレス帳を参照したり勉強したりするということは、C 言語の基本的な構文といくつかの基本的なルーチンをほぼマスターしたことになります。後で質問や提案があれば、コメント欄で議論してください。
2. ソースコード
テスト.c:
#include "contact.h" //测试通讯录 void menu() { printf("**********************************\n"); printf("****** 1.add 2.del ******\n"); printf("****** 3.search 4.modify ******\n"); printf("****** 5.show 0.exit ******\n"); printf("**********************************\n"); printf("**********************************\n"); } void test() { int input = 0; Contact con; InitContact(&con);//初始化通讯录结构体 do { menu(); printf("请选择:>"); scanf("%d", &input); switch (input) { case 1: AddContact(&con); break; case 2: DelContact(&con); break; case 3: SearchContact(&con); break; case 4: ModifyContact(&con); break; case 5: ShowContact(&con); break; case 0: printf("退出成功!\n"); break; default: printf("输入无效,请重新选择!\n"); break; } } while (input); } int main() { test(); return 0; }
連絡先.c:
//函数的实现 #include "Contact.h" //初始化通讯录结构体 void InitContact(Contact* p) { memset(p->data, 0, sizeof(p->data)); p->sz = 0; } //增加联系人信息 void AddContact(Contact* p) { //判断通讯录是否塞满 if (p->sz == Max) { printf("通讯录已满,无法添加\n"); return; } printf("请输入要添加的联系人的姓名:>"); scanf("%s", p->data[p->sz].name); printf("请输入要添加的联系人的性别:>"); scanf("%s", p->data[p->sz].sex); printf("请输入要添加的联系人的电话号码:>"); scanf("%s", p->data[p->sz].tala); printf("请输入要添加的联系人的地址:>"); scanf("%s", p->data[p->sz].addr); p->sz++; printf("添加联系人成功!\n"); } //展示联系人信息 void ShowContact(const Contact* p) { //显示标题 printf("%-5s\t%-5s\t%-12s\t%-10s\n", "姓名", "性别", "电话号码", "地址"); for (int i = 0; i < p->sz; i++) { printf("%-5s\t%-5s\t%-12s\t%-10s\n", p->data[i].name, p->data[i].sex, p->data[i].tala, p->data[i].addr); } } //查找联系人 int Findname(Contact* p, char name1[]) { int i = 0; for (i = 0; i < p->sz; i++) { if (strcmp(p->data[i].name, name1) == 0) { return i; } } //没找到 return -1; } //删除指定联系人信息 void DelContact(Contact* p) { if (p->sz == 0) { printf("通讯录为空!\n"); return; } char name1[Max_name] = { 0 }; printf("请输入你要删除的联系人姓名:>"); scanf("%s", name1); int del = Findname(p, name1); if (del == -1) { printf("该通讯录不存在这个人!\n"); return; } int i = 0; for (i = del; i < p->sz - 1; i++) { p->data[i] = p->data[i + 1]; } p->sz--; printf("删除联系人成功!\n"); } //查找指定联系人 void SearchContact(const Contact* p) { char name[Max_name] = { 0 }; printf("请输入你要查看的联系人的姓名:>"); while (getchar()!= '\n'); scanf("%s", name); int i = Findname(p, name); if (i == -1) { printf("该通讯录不存在该联系人\n"); } else { //显示标题 printf("%-5s\t%-5s\t%-12s\t%-10s\n", "姓名", "性别", "电话号码", "地址"); printf("%-5s\t%-5s\t%-12s\t%-10s\n", p->data[i].name, p->data[i].sex, p->data[i].tala, p->data[i].addr); } } //修改联系人信息 void ModifyContact(Contact* p) { char name[Max_name] = { 0 }; printf("请输入你要修改的联系人的姓名:>"); while (getchar() != '\n'); scanf("%s", name); int i = Findname(p, name); if (i == -1) { printf("该通讯录不存在该联系人\n"); } else { printf("请重新输入该联系人的姓名:>"); scanf("%s", p->data[i].name); printf("请重新输入该联系人的性别:>"); scanf("%s", p->data[i].sex); printf("请重新输入该联系人的电话号码:>"); scanf("%s", p->data[i].tala); printf("请重新输入该联系人的地址:>"); scanf("%s", p->data[i].addr); } printf("修改成功!\n"); }
連絡先.h:
#define _CRT_SECURE_NO_WARNINGS 1 #pragma once #define Max 100 #define Max_name 20 #define Max_sex 5 #define Max_tele 12 #define Max_addr 30 //存放函数的类型和声明 #include<string.h> #include<stdio.h> typedef struct PeoInfo { char name[Max_name]; char sex[Max_sex]; char tala[Max_tele]; char addr[Max_addr]; }PeoInfo; //通讯录结构体 typedef struct Contact { PeoInfo data[Max]; int sz; }Contact; //函数声明 //初始化通讯录结构体 void InitContact(Contact* p); //增加联系人信息 void AddContact(Contact* p); //展示联系人信息 void ShowContact(Contact* p); //删除联系人信息 void DelContact(Contact* p); //查找指定联系人信息 void SearchContact(const Contact* p); //修改联系人信息 void ModifyContact(Contact* p);
コードの実行結果:
3. 気づき始める
1.基本的な枠組み:
このアドレス帳の実装では、マルチファイル メソッドが使用されています。アドレス帳については誰もが学習しているため、ほぼすべてのアドレス帳がマルチファイル操作にさらされるはずです。いわゆるマルチファイル操作は次のとおりです。
①:関数宣言、マクロ定義定義、構造体宣言等を.hファイルに記述します。(contact.h)
②: 関数の定義は .c ファイルに配置されます。(連絡先.c)
③: main 関数といくつかの基本的なフレームワークを別の .c ファイルに個別に配置できます。(テスト.c)。
これはアドレス帳なので、アドレス帳の人物を保存する構造と、人事情報を保存する構造が必要です。宣言は contact.h ファイルに配置されます。
①:この人事情報は名前、性別、電話番号、住所などの構造体 PerInfo に入れていますが、その他の情報も自由に追加できます。
②: 次に、2 番目の構造体 Contact は連絡先を保存するために使用されます。ここでは、連絡先の上限が 100 であることを例として、メンバーには PerInfo 構造体配列があり、既存の人数を記録するために使用される整数変数 sz があります。 、人を増やす、sz+1、人を削除する、sz-1。
コードは以下のように表示されます:
#pragma once #define Max 100 #define Max_name 20 #define Max_sex 5 #define Max_tele 12 #define Max_addr 30 typedef struct PeoInfo { char name[Max_name]; char sex[Max_sex]; char tala[Max_tele]; char addr[Max_addr]; }PeoInfo; //通讯录结构体 typedef struct Contact { PeoInfo data[Max]; int sz; }Contact;
その後、このフレームワークは引き続き do while ループを使用して switch case ステートメントをカバーし、さまざまな関数の選択を容易にします。ここでは、それを test.c ファイルに記述します。
#include "contact.h" //测试通讯录 void menu() { printf("**********************************\n"); printf("****** 1.add 2.del ******\n"); printf("****** 3.search 4.modify ******\n"); printf("****** 5.show 0.exit ******\n"); printf("**********************************\n"); printf("**********************************\n"); } void test() { int input = 0; Contact con; InitContact(&con);//初始化通讯录结构体 do { menu(); printf("请选择:>"); scanf("%d", &input); switch (input) { case 1: break; case 2: break; case 3: break; case 4: break; case 5: break; case 0: break; default: break; } } while (input); } int main() { test(); return 0; }
①:当該ヘッダファイルはcontact.hファイル内にあるため、contact.cファイル内でもtest内でも問題ありません。c ファイルに独自のヘッダー ファイル contact.h をインクルードする必要があります。
②: 次に、見た目を良くするために、自分で設定できるメニュー関数メニューを書きます。
③: まず Contact 構造体変数 con を用意し、次に InitContact 関数を作成してそのメンバーを単純に初期化する必要があります。
ここの配列はスペースが100個あり、ループの初期化が面倒なので、ライブラリ関数 memset を使用します。
④: ほとんどの人は do while を使用してスイッチのケースを設定する必要があります。この方法では、メニュー機能に従って選択し、異なる数値を入力して異なる関数機能を入力し、関数の終了後にループで入力できるからです。 0を入力するとdo while終了、つまりシステム全体が終了します。
2. 連絡先を追加します。
基本的なフレームワークが構築されたら、関連する関数を実装しますが、同様のプログラムを作成する場合、デバッグと修正を容易にするために、一度に 1 つの関数ずつ実装することをお勧めします。
まず、追加操作を実装するために、追加操作を実装するための AddContact 関数を作成します。関数のソース コードは次のとおりです。
//增加联系人信息 void AddContact(Contact* p) { //判断通讯录是否塞满 if (p->sz == Max) { printf("通讯录已满,无法添加\n"); return; } printf("请输入要添加的联系人的姓名:>"); scanf("%s", p->data[p->sz].name); printf("请输入要添加的联系人的性别:>"); scanf("%s", p->data[p->sz].sex); printf("请输入要添加的联系人的电话号码:>"); scanf("%s", p->data[p->sz].tala); printf("请输入要添加的联系人的地址:>"); scanf("%s", p->data[p->sz].addr); p->sz++; printf("添加联系人成功!\n"); }
①:追加するので、まずアドレス帳がいっぱいかどうかを判断する必要がありますが、いっぱいでなければ追加を続けるのでif文から始めます sz==Maxのときはいっぱいです。
②:後は対応する位置に順番にデータを入力するだけです。szはアドレス帳に存在する人数を表し先頭が0で、配列の添え字も0から始まるので、直接使用します。データを入力するための配列の添字として sz を使用します。はい、加算が成功すると、sz は 1 増加します。これは人数 +1 を意味し、2 回目の加算時に配列の添字としても使用できます。
③: ここで注意しなければならないのは、各構造体の変数とメンバーの対応関係、および「.」演算子と「->」演算子です。
3. 連絡先情報を表示します。
コードが間違っているかどうかのテストを容易にするために、追加操作を実装した後に表示操作を実装すると、追加操作が間違っているかどうかを確認し、後続の関数が完了するたびに表示機能を使用できます。チェックする。
表示機能を実装する関数 ShowContact 関数を作成します。ソースコードは次のとおりです。
//展示联系人信息 void ShowContact(Contact* p) { //显示标题 printf("%-5s\t%-5s\t%-12s\t%-10s\n", "姓名", "性别", "电话号码", "地址"); //显示信息 for (int i = 0; i < p->sz; i++) { printf("%-5s\t%-5s\t%-12s\t%-10s\n", p->data[i].name, p->data[i].sex, p->data[i].tala, p->data[i].addr); } }
①:見やすいように最初にタイトルを印刷します。
②: for ループを使用し、次に sum 構造体を使用して対応する値を見つけて出力するだけです。
③: ここで注目すべきは組版の問題です。インデントや組版は見た目に影響します。自分で設定することも、アピールのソースコードを参照することもできます。
4. 連絡先情報を削除します。
削除操作を実装するための DelContact 関数を作成します。ソースコードは次のとおりです。
//删除指定联系人信息 void DelContact(Contact* p) { if (p->sz == 0) { printf("通讯录为空!\n"); return; } char name1[Max_name] = { 0 }; printf("请输入你要删除的联系人姓名:>"); scanf("%s", name1); int del = Findname(p, name1); if (del == -1) { printf("该通讯录不存在这个人!\n"); return; } int i = 0; for (i = del; i < p->sz - 1; i++) { p->data[i] = p->data[i + 1]; } p->sz--; printf("删除联系人成功!\n"); }
①: 削除なので、まずアドレス帳が空かどうかを判断する必要があります。
②: 次に、ユーザーが削除する連絡先の名前を入力するための一時配列 char name1[] を作成します。
③: 次に、この人物がアドレス帳に存在するかどうかを確認する必要があるため、ここでは指定された連絡先を検索する Findname 関数を作成します。ソース コードは次のとおりです。
//查找联系人 int Findname(Contact* p, char name1[]) { int i = 0; for (i = 0; i < p->sz; i++) { if (strcmp(p->data[i].name, name1)) { return i; } } //没找到 return -1; }
ここで注目していただきたいのは、ループ内の if 文です。判定条件に「==」を使いたがる人が多いですが、名前が文字列であることに注意する必要があります。ここでは 2 つの文字列を比較しているので、 「==」を直接使用することはできないため、ここでは文字列関数 strcmp を使用します。具体的な使用方法については、http: //t.csdn.cn/qD0LQを参照してください。
④:見つからない場合はプロンプトを表示後すぐに戻り、見つかった場合は削除操作を実行します。
配列を使用しているため、削除操作は簡単です。最初に連絡先の位置 del を見つけて、その位置以降の内容を順番に上書きするだけです。最後に、既存の人数 sz を 1 つ減らすことができます。なので、ここでは for ループを使用します。
5. 指定された連絡先情報を表示します。
この操作を実装するために SearchContact 関数を作成します。ソース コードは次のとおりです。
//查找指定联系人 void SearchContact(const Contact* p) { char name[Max_name] = { 0 }; printf("请输入你要查看的联系人的姓名:>"); while (getchar()!= '\n'); scanf("%s", name); int i = Findname(p, name); if (i == -1) { printf("该通讯录不存在该联系人\n"); } else { //显示标题 printf("%-5s\t%-5s\t%-12s\t%-10s\n", "姓名", "性别", "电话号码", "地址"); printf("%-5s\t%-5s\t%-12s\t%-10s\n", p->data[i].name, p->data[i].sex, p->data[i].tala, p->data[i].addr); } }
①: まずユーザーが指定された連絡先の名前を入力しやすくするために一時配列を作成し、次に while ループを使用してバッファー内の余分な内容を削除し、scanf が正常に読み取れるようにします。
②: 次に Findname 関数を呼び出し、戻り値に基づいて操作を実行します。
-1 が返された場合、連絡先は存在しないため、直接返されます。
-1 でない場合は、見つかったことを意味し、連絡先の情報を出力できます。
6. 連絡先情報を変更します。
この操作を実装するために ModifyContact 関数を作成します。ソース コードは次のとおりです。
//修改联系人信息 void ModifyContact(Contact* p) { char name[Max_name] = { 0 }; printf("请输入你要修改的联系人的姓名:>"); while (getchar() != '\n'); scanf("%s", name); int i = Findname(p, name); if (i == -1) { printf("该通讯录不存在该联系人\n"); } else { printf("请重新输入该联系人的姓名:>"); scanf("%s", p->data[i].name); printf("请重新输入该联系人的性别:>"); scanf("%s", p->data[i].sex); printf("请重新输入该联系人的电话号码:>"); scanf("%s", p->data[i].tala); printf("请重新输入该联系人的地址:>"); scanf("%s", p->data[i].addr); } printf("修改成功!\n"); }
①: 前のステップは連絡先の検索と同じで、ユーザーはまず変更する連絡先の名前を入力し、それが存在するかどうかを確認する必要があります。
②: 存在する場合は添字を返し、添字情報のデータを再入力するだけなので比較的簡単です。
要約する
今回は、誰もがアイデアや方法を見つけやすくするために、エディターがアドレス帳を実装しただけです。抜け穴や自分で実装できる改善点が多数あります。この知識はここで終わりです。皆さんのお役に立てれば幸いです。