chiếu thì ta phải đặt ra câu hỏi “Tham chiếu sẽ là bí danh của đối tượng nào và nó có tồn tại mỗi khi tham chiếu được sử dụng không?”.[r]
(1)(2)Nội dung chính
Con trỏ (Pointer)
Tham chiếu (Reference)
(3)1 Con trỏ
Con trỏ sử dụng để:
Truy nhập vào thành phần mảng Truyền tham số cho hàm theo kiểu truyền
biến
Truyền mảng xâu ký tự cho hàm Lấy thông tin từ nhớ hệ thống
Tạo cấu trúc liệu như: danh
(4)Con trỏ …
Mỗi biến chương trình chiếm vùng
nhớ, ví dụ biến kiểu int chiếm byte nhớ
Vị trí vùng nhớ gọi địa
biến
10101011 00001111 10001000 11100011 0x1054
0x1055 0x1056 0x1057
00111011 0x1058
int i; Địa i
(5)Biến trỏ
Biến trỏ biến lưu giá trị địa vùng
nhớ
Mỗi kiểu liệu có biến trỏ riêng:
trỏ kiểu int, trỏ kiểu char…
C++ sử dụng:
Toán tử & để lấy địa biến
Toán tử * để lấy nội dung biến trỏ
Ví dụ:
int i=17;
int* ptr; // khai báo biến trỏ kiểu int
(6)Biến trỏ …
17 0x1054
int i; int* ptr; ptr=&i;
Địa ch ỉ
cout << *ptr << endl;
(7)Biến trỏ …
int v; // khai báo biến v kiểu int int w; // khai báo biến w kiểu int
int* p; // khai báo biến p kiểu trỏ trỏ tới kiểu int p=&v; // gán địa v cho trỏ p
v=3; // gán giá trị cho v *p=7; // gán giá trị cho v
p=&w; // gán địa w cho trỏ p *p=12; // gán giá trị 12 cho w
Sử dụng tốn tử * để lấy nội dung biến cịn
(8)Con trỏ hằng
Khai báo hằng:
const int result = 5; // result
result = 10; // sau gán lại giá trị C++ báo lỗi
Khai báo trỏ hằng:
const char* answer_ptr = "Forty-Two";
// answer_ptr trỏ trỏ tới kiểu char
Dữ liệu trỏ trỏ khơng
thể thay đổi trỏ
(9)Con trỏ …
Nếu khai báo:
char *const nameptr = "Test"; //name_ptr trỏ nameptr = "New"; // sai (name_ptr hằng)
*nameptr = 'B'; // (*nameptr char)
Nếu khai báo sau khơng thể
thay đổi trỏ nội dung của trỏ:
(10)Con trỏ tham số hàm
C++ cung cấp cách truyền tham số:
Truyền tham trị: void f(int x);
(11)Con trỏ tham số hàm …
void swap( double& x, double& y) {
double tmp=x; x=y;
y=tmp; }
void swap( double* ptr1, double* ptr2) {
double tmp=*ptr1; *ptr1=*ptr2; *ptr2=tmp; }
double a=3.0; double b=5.0
(12)Con trỏ tham số hàm…
void bsort (double* ptr, int n) {
int j,k;
for (j=0; j<n-1; j++) for(k=j+1; k<n; k++) if(*(ptr+j) > *(ptr+k)) swap(ptr+j,ptr+k); }
(13)Quản lý nhớ
Toán tử new sử dụng để tạo đối
tượng vùng nhớ heap
Date* CreateDate() {
int day, month, year; char dummy;
cout << ”Enter dd/mm/yyyy :”;
cin >> day >> dummy >> month >> dummy >> year; Date* tmpptr = new Date date(day, month, year); return tmpptr;
}
Date* ptr;
ptr=CreateDate();
(14)Quản lý nhớ …
Toán tử new sử dụng để cấp phát
các block nhớ
Toán tử delete sử dụng để giải phóng
vùng nhớ cấp phát toán tử new
#include <cstring>
char* str =”This is an old C-style string”;
int len=strlen(str); // xác định kích thước str char* ptr;
ptr = new char[len+1]; // cấp phát vùng nhớ strcpy(ptr,str);
(15)Toán tử new sử dụng trong hàm tạo
class String { private: char* str; public: String(char* s) { int length=strlen(s);
str = new char[length+1]; strcpy(str,s);
}
~String() { delete [] str; }
void Display() { cout << str << endl; } };
(16)Con trỏ trỏ tới đối tượng
Con trỏ trỏ tới đối tượng tương tự
như kiểu built-in khác
Truy nhập tới thành phần thơng qua tốn
tử ->
Date date;
date.Set(12,3,1996); date.Display();
Date* dateptr;
dateptr=new Date;
(17)Ví dụ: Linked List
struct link // định nghĩa phần tử danh sách {
int data; // data item
link* next; // trỏ trỏ tới phần tử };
class linklist {
private:
link* first; // trỏ trỏ tới phần tử danh sách public:
linklist() { first = NULL;} // hàm tạo khơng có tham số
void additem(int d); // bổ sung thêm phần tử vào danh sách void display(); // hiển thị danh sách
(18)Ví dụ: Linked List …
void linklist::additem(int d) {
link* newlink = new link; // tạo phần tử danh sách newlink->data = d; // gán liệu
newlink->next=first; // trỏ vào phần tử first = newlink; // thay đổi trỏ first }
void linklist::display() {
link* current=first; // phần tử while(current != NULL) // đến kết thúc danh sách {
cout << current->data << ” ”;
(19)Cấu trúc tự trỏ
Một lớp chứa trỏ trỏ tới đối tượng
của lớp đó, khơng thể chứa đối tượng lớp
class someclass {
someclass* ptr; // };
class someclass {
(20)Ví dụ: Sử dụng cấu trúc tự trỏ
class LinkList {
private:
int data;
LinkList *next, *first; public:
LinkList();
void Insert(int d); void Show();
(21)Ví dụ: Sử dụng cấu trúc tự trỏ …
LinkList :: LinkList(){f=NULL;} void LinkList :: Insert(int d) {
LinkList* n = new LinkList(); n->data=d;
n->next=first; first=next; }
void LinkList :: Show() {
LinkList* p=first; while (p!=NULL) {
(22)2 Tham chiếu
Tham chiếu bí danh (alias)
Khi ta tạo tham chiếu, khởi tạo
bằng tên đối tượng khác (đối tượng đích)thì tham chiếu đóng vai trị tên khác đích
Bất kỳ việc thực tham chiếu
cũng tức thực đích
Khai báo tham chiếu:
(23)Tham chiếu …
Nếu ta yêu cầu tham chiếu tham
chiếu tới địa nó, tham chiếu sẽ trả địa đối tượng đích nó.
Ví dụ:
int intOne;
int& rSomeRef = intOne;
cout << "&intOne: " << &intOne << endl;
(24)Tham chiếu tới đối tượng
Bất kỳ đối tượng tham chiếu, kể đối tượng
người sử dụng định nghĩa
Tham chiếu tới đối tượng thường sử dụng đối
tượng
Dữ liệu thành phần phương thức truy nhập cách sử dụng
toán tử “.”, tham chiếu đóng vai trị bí danh đối tượng
Ví dụ:
int& rIntRef = int; // sai int howBig = 200;
int& rIntRef = howBig;
Tương tự, khởi tạo tham chiếu tới lớp CAT:
CAT& rCatRef = CAT; // sai
Phải khởi tạo rCatRef tới đối tượng CAT cụ thể
(25)Con trỏ Null tham chiếu Null
Khi trỏ khơng khởi tạo bị xố
thì chúng gán Null
Tuy nhiên, tham chiếu Null Một chương trình có tham chiếu tới đối
(26)3 Sử dụng tham chiếu hay con trỏ
Người lập trình C++ thích tham chiếu trỏ
Tham chiếu thường rõ ràng, dễ sử dụng thực
hiện nhiệm vụ che dấu thông tin tốt
Không thể gán lại tham chiếu Nếu ta cần trỏ tới
đối tượng sau lại trỏ tới đối tượng khác, ta phải sử dụng trỏ
Tham chiếu khơng thể null, có trường
hợp đối tượng null ta phải sử dụng trỏ
Ví dụ:
(27)Sử dụng tham chiếu hay trỏ …
Ta khai báo trỏ tham chiếu
danh sách tham số hàm, với đối tượng truyền trị khác
Ví dụ:
CAT * SomeFunction (Person& theOwner, House* theHouse, int age);
SomeFunction có tham số:
Tham số thứ tham chiếu tới đối tượng Person Tham số thứ hai trỏ tới đối tượng House
Tham số thứ ba số nguyên
Hàm trả trỏ trỏ tới đối tượng CAT
Trước truyền tham chiếu cho hàm trả tham