Chuyển đổi kiểu

Một phần của tài liệu Lập trình hướng đối tượng (Trang 76 - 85)

Có các loại chuyển đổi kiểu sau đây: 1- Chuyển từ kiểu cơ sở sang kiểu cơ sở. 2- Chuyển từ kiểu lớp sang kiểu cơ sở. 3- Chuyển từ kiểu cơ sở sang kiểu lớp. 4- Chuyển từ kiểu lớp sang kiểu lớp.

6.1. Chuyển từ kiểu cơ sở sang kiểu cơ sở.

- Riêng đối với việc chuyển từ kiểu cơ sở sang kiểu cơ sở là do ngôn ngữ tự động hoặc do ép kiểu.

+ Tự động chuyển kiểu theo nguyên tắc: char  int  long  float  double

+ Chuyển kiểu đợc sử dụng trong lời gọi hàm để ép kiểu của biến truyền vào hàm cùng kiểu với tham số hình thức trong hàm.

6.2. Chuyển từ kiểu lớp sang kiểu cơ sở. Nguyên tắc

Trong lớp có toán tử quy hồi kiểu: là toán tử tải bội, bổ sung định nghĩa toán tử kiểu cơ sở.

Khai báo

class class_name; {...

opearator type_name() ...

};

Định nghĩa

type_name class_name::type_name() { // nội dung toán tử}

Ví dụ 1 Chuyển từ kiểu VECTOR sang kiểu double

class VECTOR { private: int n; float *v; public: ... operator double() ... }; double VECTOR::double() { int i; double s=0;

for(i=0;i<n;s += v[i]*v[i], i++); return s;} Cụ thể ta có chơng trình sau: #include <iostream.h> #include <conio.h> const maxsize=10; class VECTOR { int n; float *v; public:

VECTOR() {v =new float[maxsize];} ~VECTOR() { delete v ;}

friend ostream& operator << (ostream&, VECTOR &); friend istream& operator >> (istream&, VECTOR &); operator double();

double VECTOR::operator double() { double s=0; int i;

for(i=0;i<n;s+=v[i]*v[i],i++); return s;}

ostream& operator << (ostream &dout, VECTOR &b) { int i;

for(i=0;i<b.n;i++) dout<<b.v[i]<<" "; dout<<endl;

return dout;}

istream& operator >> (istream &din, VECTOR &b) { int i,x; cout<<"n= "; cin>>x; b.n=x; for(i=0;i<b.n;i++) {cout<<"vector["<<i+1<<"] ="; din>>x; b.v[i]=x; } return din;} int main() { clrscr(); VECTOR a; cin>>a; cout<<a<<endl; double d=a; cout<<d<<endl; getch(); return 0; }

6.3. Chuyển từ kiểu cơ sở sang kiểu lớp.

Nguyên tắc

Trong lớp sử dụng constructor khởi tạo mà tham số của constructor là kiểu cơ sở.

Ví dụ 2: Chuyển từ char* sang kiểu String thông qua constructor String(char *S)

String::String(char *S) { len=strlen(S);

text = new char[len+1]; strcpy(text,S);

}

6.4. Chuyển từ kiểu lớp sang kiểu lớp

Nguyên tắc

Để chuyển từ lớp X sang lớp Y, trong lớp Y phải có constructor khởi tạo đặc biệt nhận đối là đối tợng của lớp X. class X {// nội dung lớp X }; class Y {... Y(X x); // chuyển từ lớp X  lớp Y ... }; void main() { X a; Y b=a; ... } Ví dụ 3 (chkieu2.cpp)

Cho lớp MH1: Mã hàng, Số lợng và Đơn giá

và lớp MH2: Mã hàng, Tổng giá trị (Tổng giá trị = Số lợng * Đơn giá)

#include <iostream.h> #include <conio.h> #include <stdio.h> class MH1 { int code; int num; float price; public: MH1() {code=num=price=0;}

MH1(int c, int n, float p) { code=c; num=n; price=p; } void get_data()

{ cout << " code = "; scanf("%d",&code); cout << " num = "; scanf("%d",&num); cout << " price = "; scanf("%f",&price); }

void show(void)

{ cout << " code: " << code << endl << " num : " << num << endl << " price : " << price << endl; }

int get_code() { return code ;} int get_num() { return num ;} float get_price() { return price ;}

operator double() { return num*price ;} }; class MH2 { int code; double total; public: MH2() {code=total=0;}

MH2(int c, double t) { code=c; total=t; } MH2(MH1 p)

{ code = p.get_code();

total= p.get_num()*p.get_price(); }

{ cout << " code: " << code << endl << " total : " << total << endl; } }; int main() { MH1 m(4,20,35.6); MH2 n=m; m.show(); n.show(); MH1 a[3]; int i; for(i=0;i<3;i++) a[i].get_data(); double s=0; for(i=0;i<3;i++) s+=a[i]; cout<<"s = " <<s<<endl; getche(); return 0;}

Để chuyển từ lớp X sang lớp Y có trờng hợp phải sử dụng cách 2:

- Trong lớp X phải có toán tử tải bội để mở rộng định nghĩa kiểuY. (Giống nh chuyển từ kiểu lớp sang kiểu cơ sở, nhng lúc này kiểu cơ sở chính là kiểu lớp Y đã định nghĩa.)

- Trong lớp Y đồng thời phải nhận hàm - toán tử này (của lớp X) là một hàm thân thiện - tức là hàm này của X là bạn của Y , nếu nó nhu cầu có sử dụng dữ liệu private của Y.

class Y; // khai báo trớc lớp Y //---

class X {...

operator Y(); //Y đợc coi là kiểu dữ liệu mới , chuyển từ // kiểu X sang kiểu Y

... }; class Y { ...

friend X::operator Y(); ...

};

X::operator Y()

{ // nội dung toán tử Y(), sử dụng đợc dữ liệu riêng của Y }

Ví dụ 4 (chkieu3.cpp)

Hãy chuyển từ lớp điểm (POINT) sang lớp số phức (COMPLEX) #include <iostream.h> #include <conio.h> #include <math.h> class COMPLEX; class POINT { int x,y; public:

POINT(int ox=0,int oy=0) { x=ox;y=oy;} operator COMPLEX();

};

class COMPLEX { float a,b; public:

COMPLEX(float a1=0,float b1=0) {a=a1;b=b1;} friend POINT::operator COMPLEX();

void display() {cout<<a<<" + i * "<<b<<endl;} };

POINT::operator COMPLEX() { COMPLEX C(x,y); return C; } int main() { clrscr(); POINT a(2,5); COMPLEX C; C=(COMPLEX)a; C.display(); getche(); return 0;}

Bài 4. Vài vấn đề về sử dụng từ khoá const

1. Sử dụng biến kiểu const

- Trong C và C++ các biến kiểu const không đợc phép thay đổi trong suốt quá trình chơng trình thực hiện.

- Phạm vi của các giá trị const trong C và C++ khác nhau:

+ Trong C, các giá trị const có phạm vi toàn cục, nghĩa là chúng có thể nhìn thấy ở các files khác, trừ khi nó đợc khai báo là static

Ví dụ 1: (trong C)

const int i=5; /* cac files khac deu nhan biet duoc i=5 */

static const int i = 5; /*cac file khac khong nhan biet duoc i=5 */

+ Trong C++, các giá trị const có phạm vi hoạt động cục bộ trong file chúng đợc khai báo. Để các file khác có thể nhìn thấy giá trị const của file hiện tại này thì nó phải đợc khai báo sau extern và các file đó phải nhắc lại khai báo extern const này, nhng không đợc viết lại giá trị hằng.

Ví dụ 2: (trong C++)

const int i=5; /* cac files khac khong nhan biet duoc i=5 */

extern const int i = 5;

/* cac files khac deu nhan biet duoc i = 5 neu các file khac do phai nhac lai const i, nhung khong chi ra gia tri cua i */

extern const int i;

- Điều lu ý: các biến kiểu const trong hàm trong C+ + luôn luôn có phạm vi hoạt động cục bộ trong hàm đó.

Một cách logic suy ra là nó không đợc khai báo extern trong hàm, nghĩa là mọi const là extern phải đợc khai báo trớc tất cả các hàm.

- Tiện lợi của khai báo const: Một biến khai báo kiểu const tiện lợi hơn so với việc sử dụng chỉ thị #define để khai báo hằng. Bởi vì khi khai báo một biến kiểu const thì ngoài việc giá trị của nó không thay đổi trong quá trình thực hiện chơng trình, trình biên dịch còn có thể thực hiện việc kiểm tra kiểu của biến và tuy thế vẫn không cấp phát bộ nhớ cho các biến này khi không cần thiết.

Ví dụ 3:

const int TRUE = 1 const int FALSE = 0

while (TRUE) {... int a = FALSE ; }

các biến TRUE và FALSE sẽ đợc thay thế bằng các giá trị khi biên dịch mà không cần phải phân bố bộ nhớ cho chúng.

- Để có thể phân bố bộ nhớ cho một biến int i kiểu const ta cần phải khai báo nh sau:

const int& i = 9;

Theo cách này, i đợc xem nh tất cả các biến tham chiếu khác chỉ có một điều khác biệt là giá trị của nó không đợc phép thay đổi khi thực hiện chơng trình.

Một phần của tài liệu Lập trình hướng đối tượng (Trang 76 - 85)

Tải bản đầy đủ (DOC)

(174 trang)
w