Ngô Thị Lan và Đtg<br />
<br />
Tạp chí KHOA HỌC & CÔNG NGHỆ<br />
<br />
99(11): 73 - 78<br />
<br />
ÁP DỤNG MẪU THIẾT KẾ TRONG XỬ LÝ PHÂN TÁN<br />
Ngô Thị Lan*, Phạm Thị Thương, Lê Thu Trang<br />
Trường Đại học Công nghệ thông tin và Truyền thông – ĐH Thái Nguyên<br />
<br />
TÓM TẮT<br />
Hiện nay hầu hết các hệ thống thông tin đều được xây dựng phân tán. Phát triển một hệ thống phân<br />
tán là khó khăn do tính phức tạp vốn có của việc giao tiếp phân tán. Mặt khác phần mềm hiện đại<br />
ngày càng đòi hỏi tính linh động, mở rộng cao để sẵn sàng đáp ứng được các yêu cầu thường<br />
xuyên thay đổi của người sử dụng. Một yêu cầu không thể thiếu đối với phần mềm hiện đại là tính<br />
tái sử dụng cao. Mẫu thiết kế được coi là giải pháp hữu hiệu để nâng cao tính tái sử dụng của phần<br />
mềm. Trong bài báo này, chúng tôi trình bày kết quả nghiên cứu của mình về việc áp dụng mẫu<br />
thiết kế trong tiến trình xây dựng và phát triển hệ thống phân tán sao cho hệ thống có khả năng tái<br />
sử dụng và bảo trì cao.<br />
Từ khóa: Xử lý phân tán, mẫu thiết kế, hệ thống phân tán, giao tiếp phân tán, chia sẻ tài nguyên<br />
<br />
ĐẶT VẤN ĐỀ*<br />
Phát triển một hệ thống phân tán là khó khăn<br />
do tính phức tạp vốn có của việc giao tiếp<br />
phân tán. Xây dựng một hệ thống phân tán có<br />
khả năng mở rộng, linh động, dễ sửa đổi còn<br />
khó hơn. Erich Gamma cùng các đồng sự đã<br />
đề xuất 23 mẫu thiết kế, nhằm đáp ứng được<br />
nhiều yêu cầu đối với sản phẩm phần mềm:<br />
dễ bảo trì, dễ nâng cấp, chất lượng cao và tiết<br />
kiệm thời gian…Trong đó, đáp ứng được tiêu<br />
chí quan trọng là khả năng sử dụng lại các<br />
đơn thể, thừa kế được các kinh nghiệm của<br />
các chuyên gia trong quá trình phát triển phần<br />
mềm [5]. Trong bài báo này chúng tôi<br />
nghiên cứu áp dụng mẫu thiết kế vào giải<br />
quyết một số vấn đề cơ bản khi thiết kế hệ<br />
thống phân tán.<br />
Bài báo có cấu trúc như sau: Sau phần đặt vấn<br />
đề là phần trình bày về hệ phân tán và các vấn<br />
đề của hệ phân tán. Tiếp theo, chúng tôi trình<br />
bày tổng quan về mẫu thiết kế. Trong phần kế<br />
tiếp, chúng tôi trình bày về cách áp dụng các<br />
mẫu thiết kế vào giải quyết một số vấn đề cụ<br />
thể của hệ thống phân tán. Cuối cùng là thảo<br />
luận và tài liệu tham khảo.<br />
CÁC VẤN ĐỀ CƠ BẢN CỦA HỆ PHÂN TÁN<br />
Một hệ thống phân tán là một hệ thống máy<br />
tính, trong đó một số thành phần hợp tác bằng<br />
cách giao tiếp qua mạng. Nói một cách tổng<br />
quát hơn thì hệ thống phân tán là một hệ<br />
*<br />
<br />
Tel: 0943 870272, Email: ntlan@ictu.edu.vn<br />
<br />
thống gồm các thành phần xử lý phân tán,<br />
giao tiếp với nhau qua một cơ sở hạ tầng<br />
truyền thông chung (www, internet, mạng<br />
điện thoại…..) [6].<br />
Các vấn đề của hệ phân tán:<br />
- Tính chia sẻ tài nguyên: Hệ thống phân tán<br />
phải chia sẻ được tài nguyên trong hệ thống.<br />
- Tính mở: Hệ thống có thể dễ dàng bổ sung<br />
thêm dịch vụ mới mà không ảnh hưởng tới<br />
các hoạt động đã có.<br />
- Tính tương tranh: Trong hệ phân tán ta cần<br />
xử lý được tính tương tranh, tính đồng bộ của<br />
hệ thống.<br />
- Khả năng thay đổi quy mô.<br />
- Khả năng chịu lỗi: Hệ thống phân tán có<br />
nguy cơ mất an toàn rất lớn. Vì vậy đòi hỏi hệ<br />
thống phải có khả năng chịu lỗi cao.<br />
- Tính co dãn: Thể hiện khả năng tương thích<br />
của hệ thống.<br />
- Tính trong suốt: Ẩn giấu sự rời rạc và những<br />
nhược điểm nếu có của hệ phân tán đối với<br />
người sử dụng (end-user) và những nhà lập<br />
trình ứng dụng.<br />
MẪU THIẾT KẾ<br />
Định nghĩa về mẫu thiết kế<br />
Mẫu thiết kế là cặp bài toán (vấn đề) và giải<br />
pháp cho một vấn đề thiết kế thông dụng. Nó<br />
không đơn thuần là một bước nào đó trong<br />
các giai đoạn phát triển phần mềm và cũng<br />
không phải là luật mà là các ý tưởng, sáng<br />
kiến kinh nghiệm đã được kiểm tra, đúc kết<br />
73<br />
<br />
Ngô Thị Lan và Đtg<br />
<br />
Tạp chí KHOA HỌC & CÔNG NGHỆ<br />
<br />
qua thực tế. Nó là lời khuyên cho người thiết<br />
kế phần mềm áp dụng vào ngữ cảnh cụ thể.<br />
Mỗi mẫu mô tả một vấn đề xảy ra lặp đi lặp<br />
lại, và mô tả cốt lõi giải pháp của vấn đề đó,<br />
ta có thể sử dụng một mẫu hơn triệu lần mà<br />
không bao giờ thực hiện hai lần giống nhau [5].<br />
Sự góp mặt của mẫu thiết kế sẽ giúp cho việc<br />
xác định bài toán cần giải quyết nhanh gọn<br />
hơn, từ đó đưa ra cách giải quyết hợp lý sao<br />
cho phần mềm được xây dựng có tính tái sử<br />
dụng cao, tránh bị thoái hóa thiết kế.<br />
Các yếu tố xác định mẫu thiết kế<br />
Một mẫu thiết kế được xác định qua các yếu<br />
tố sau:<br />
- Tên mẫu (pattern name): Mỗi mẫu đặc trưng<br />
bởi tên của nó. Dựa vào tên mẫu ta có thể<br />
hình dung một cách nhanh chóng và hiệu quả<br />
về mẫu.<br />
- Vấn đề (Problem): Mô tả tình huống áp<br />
dụng mẫu.<br />
- Giải pháp (Solution): Thể hiện các lớp và<br />
đối tượng tham gia giải quyết vấn đề và mối<br />
quan hệ, trách nhiệm của các thành phần tham<br />
gia vào mẫu. Mẫu cung cấp một mô tả trừu<br />
tượng của vấn đề được thiết kế và việc sắp xếp<br />
các phần tử cần thiết để giải quyết vấn đề đó.<br />
- Kết quả: Cho chúng ta thấy việc áp dụng<br />
các giải pháp để giải quyết các vấn đề đặt ra<br />
có hiệu quả hay không. Kết quả sẽ đặt ra cho<br />
chúng ta các lựa chọn, để từ đó có thể xem<br />
xét lựa chọn nào là phù hợp nhất, tốt nhất.<br />
Các bước để lựa chọn mẫu thiết kế<br />
Để lựa chọn mẫu thiết kế phù hợp với ngữ<br />
cảnh cụ thể của hệ thống ta thực hiện các<br />
bước sau: [9]<br />
- Xác định được cần thiết kế gì, các vấn đề<br />
phát sinh trong khi thiết kế, các vấn đề đó<br />
thuộc loại nào và tham khảo xem ứng với loại<br />
vấn đề đó có thể dùng mẫu nào để giải quyết.<br />
- Tham khảo lần lượt từng mẫu được chọn,<br />
xem mục đích sử dụng, đối chiếu với các vấn<br />
đề thiết kế gặp phải (Design Problems). Bước<br />
này giúp ta hiểu rõ hơn về các mẫu và tác<br />
dụng thực của mẫu lên vấn đề cần giải quyết.<br />
- Tìm hiểu sự tương tác giữa các mẫu thiết kế<br />
để xác định được các nhóm mẫu phù hợp với<br />
bài toán của mình.<br />
74<br />
<br />
99(11): 73 - 78<br />
<br />
- Cố gắng tìm kiếm, khảo sát các nguyên nhân<br />
có thể dẫn tới việc thoái hóa thiết kế<br />
(redesigning) để cô lập hóa, nhằm tránh các<br />
thay đổi không cần thiết.<br />
- Xác định các thành phần (module, lớp đối<br />
tượng…) có thể thay đổi trong tương lai. Từ<br />
đó quyết định xem phải làm gì để có thể thay<br />
đổi hệ thống mà không cần phải thiết kế lại.<br />
ÁP DỤNG MẪU THIẾT KẾ TRONG XỬ<br />
LÝ PHÂN TÁN<br />
Hệ thống phân tán thông thường được xây<br />
dựng trên mô hình client – server và truyền<br />
thông với nhau qua giao thức TCP/IP. Server<br />
sẽ chịu trách nhiệm trả lời các yêu cầu của<br />
client. Khi thiết kế phía server nên thiết kế<br />
sao cho độ ghép cặp thấp để dễ mở rộng trong<br />
tương lai nhưng phải kết dính chặt với các<br />
chức năng sẽ bổ sung. Đồng thời, các thành<br />
phần khác nhau phía server nên thiết kế sao<br />
cho dễ dàng chuyển giao. Client sẽ cung cấp<br />
các yêu cầu dữ liệu đến server, xử lý các phản<br />
hồi từ server.<br />
Để thực hiện giao tiếp giữa server và client<br />
trở nên trong suốt đối với người dùng và tối<br />
ưu thời gian xử lý của hệ thống khi client truy<br />
xuất các tài nguyên hay yêu cầu các dịch vụ<br />
từ server thì chúng ta sử dụng mẫu proxy.<br />
Proxy trì hoãn việc khởi tạo đối tượng cho<br />
đến khi cần thiết nó sẽ chuyển lời gọi hàm tới<br />
đối tượng mà nó đại diện để yêu cầu khởi tạo.<br />
Mặt khác khi dùng mẫu proxy ta có thể hạn<br />
chế được các nguy cơ mất an toàn đối với<br />
server do client truy cập đến. Do proxy có thể<br />
thực hiện các chính sách được thiết lập cho hệ<br />
thống trước khi thực hiện yêu cầu của Client.<br />
Nếu server phát hiện có tấn công phá hoại từ<br />
một client nào đó thông qua proxy, thì server<br />
chỉ cần xóa bỏ tiến trình của proxy hiện tại để<br />
chấm dứt cuộc tấn công [1,3].<br />
- Client Object: yêu cầu một dịch vụ từ server<br />
và triệu gọi một phương thức của nó.<br />
- Server Object: Cung cấp dịch vụ cho Client<br />
Object.<br />
- Client-Side Proxy: Đại diện cho đối tượng<br />
của client. Nó chịu trách nhiệm truyền đối số<br />
cho đối tượng cục bộ từ xa (remote object<br />
location). Nó sử dụng đối tượng tham chiếu<br />
Reference Manager để chuyển đổi đối tượng<br />
tham chiếu gửi tới tên phân tán (distributed<br />
<br />
Ngô Thị Lan và Đtg<br />
<br />
Tạp chí KHOA HỌC & CÔNG NGHỆ<br />
<br />
99(11): 73 - 78<br />
<br />
names) và nhận distributed names từ đối<br />
tượng tham chiếu. Nó cũng sử dụng<br />
Reference Manager để lấy một một đối tượng<br />
Data Interface.<br />
ClientObject<br />
<br />
ReenceInterface<br />
+m()<br />
<br />
Client-SideProxy<br />
<br />
ServerObject<br />
<br />
+convertArgument()<br />
<br />
DataInterface<br />
<br />
ReferenceManager<br />
<br />
+invoke()<br />
<br />
Client-SideCommunicator<br />
+marshaling()<br />
+unMarshaling()<br />
+sendMessage()<br />
<br />
Server-SideProxy<br />
+convertArguments()<br />
<br />
Server-SideCommunication<br />
+marshaling()<br />
+unMarshaling()<br />
+returnMessage()<br />
<br />
Hình 1: Cấu trúc mẫu proxy trong xử lý phân tán<br />
<br />
- Server-Side Proxy: chịu trách nhiệm hỗ trợ<br />
phân tán cho đối tượng Server Object trên<br />
server. Nó là điểm truy cập cho yêu cầu từ xa<br />
tới server.<br />
- Reference Manager: Chịu trách nhiệm kết<br />
nối với đối tượng tham chiếu cục bộ và proxy,<br />
với distributed names.<br />
- Client-Side Communicator và ServerSideCommunicator: Chịu trách nhiệm cài đặt<br />
giao tiếp phân tán ở tầng vật lý.<br />
Để xử lý các trường hợp nhiều đối tượng liên<br />
quan đến nhau mà khi một đối tượng trong số<br />
đó thay đổi trạng thái thì các đối tượng còn lại<br />
cần biết được và cập nhập theo thì ta sử dụng<br />
mẫu Observer. Trong hệ phân tán, ta cần đồng<br />
bộ một số đối tượng ở server và client.<br />
Các đối tượng trong phần 1 (hình 2) được<br />
thiết kế bên server thì các đối tượng trong<br />
phần 2 (hình 2) sẽ được thiết kế bên client và<br />
ngược lại.<br />
Tần suất sử dụng mẫu Observer là cao. Tuy<br />
nhiên, trong hệ thống phân tán khi sử dụng<br />
mẫu Observer, ta cần chú ý một số vần đề nảy<br />
sinh sau:<br />
<br />
Hình 2: Mẫu Observer trong hệ thống phân tán<br />
<br />
- Đố tượng Subject và Observer có thể được<br />
đặt ở các nút mạng khác nhau.<br />
- Giao tiếp giữa 2 bên có tốc độ khác nhau,<br />
giao tiếp không đáng tin cậy và khả năng của<br />
các bên là giới hạn.<br />
Khi đó, để giải quết các vấn đề trên, ta cố<br />
gắng giảm số lượng cập nhập, giảm kích<br />
thước của các cập nhập, giảm số lượng các<br />
đối tượng Observer. Khi các cập nhập quá<br />
phức tạp ta có thể kết hợp mẫu Meditor. Sử<br />
dụng mẫu Meditor để quản lý các thay đổi<br />
cần thực hiện.<br />
Obsever<br />
+update(Subjects)<br />
<br />
ChangeManager<br />
<br />
Subjects<br />
<br />
+subject -subjectObserverMapping<br />
+attach(Observer o)<br />
+detach(Observer o) +observer<br />
+notyfy()<br />
<br />
+Register(Subjects, Observer)<br />
+unregister(Subjects, Observer)<br />
+notyfy()<br />
<br />
SimpleChangeManager<br />
<br />
DAGChangeManager<br />
<br />
+Register(Subjects, Observer)<br />
+unRegister(Subjects, Observer)<br />
+notyfy()<br />
<br />
+Register(Subjects, Observer)<br />
+unRegister(Subjects, Observer)<br />
+notyfy()<br />
<br />
Hình 3: Mẫu Observer khi chiến lược update<br />
phức tạp<br />
<br />
Mẫu Command đóng gói các yêu cầu vào<br />
trong các đối tượng riêng biệt. Trong hệ thống<br />
phân tán, ta sử dụng mẫu Command để quản<br />
lý các yêu cầu từ phía client gửi đến, quản lý<br />
đăng nhập, thực hiện hủy thao tác (undo)<br />
75<br />
<br />
Ngô Thị Lan và Đtg<br />
<br />
Tạp chí KHOA HỌC & CÔNG NGHỆ<br />
<br />
hoặc lấy lại thao tác vừa hủy (redo) hoặc khi<br />
cần thực hiện chậm các yêu cầu (Command sẽ<br />
đưa các yêu cầu vào hàng đợi và thực thi sau).<br />
Nhờ mẫu này mà khi muốn mở rộng chương<br />
trình thêm các yêu cầu mới vào ta không phải<br />
sửa lại chương trình mà chỉ cần thay đổi ở lớp<br />
Command.<br />
<br />
Hình 4: Mẫu Command<br />
<br />
Đối tượng Client yêu cầu tạo Command trên<br />
nút nhận cục bộ (local Receiver node). Đối<br />
tượng Receiver phải cung cấp tập các yêu cầu<br />
cụ thể (ConcreteCommand), chỉ tạo yêu cầu<br />
khi cần truyền đi. Việc tạo và điều phối các<br />
yêu cầu được thực hiện tại client.<br />
Trong hệ phân tán, client gửi yêu cầu tới<br />
server, server gửi kết quả trả về cho client.<br />
Yêu cầu gửi server và kết quả trả về có thể<br />
hiển thị ở các định dạng khác nhau. Ta sử<br />
dụng mẫu Strategy để xác định các thuật toán<br />
hiển thị, thực hiện đóng gói đối với từng thuật<br />
toán, cho phép client lựa chọn thuật toán cụ<br />
thể trong số đó để sử dụng.<br />
<br />
99(11): 73 - 78<br />
<br />
dữ liệu ta dùng mẫu Sinleton để tạo ra một thể<br />
hiện duy nhất của cơ sở dữ liệu.<br />
Ta có thể sử dụng mẫu MVC (Model – View<br />
– Controller) để tách các thành phần mô hình,<br />
trình diễn, điều khiển riêng biệt, giúp hệ<br />
thống dễ xây dựng và bảo trì hay mở rộng.<br />
Mẫu MVC có 3 thành phần:<br />
- Model nắm giữ dữ liệu.<br />
- View: (tầng giao diện) hiển thị các dữ liệu<br />
trong Model theo Controller.<br />
- Controller điều khiển việc tương tác giữa<br />
đối tượng giao diện với người sử dụng cũng<br />
như những đối tượng khác.<br />
Mẫu MVC thường sử dụng mẫu Observer<br />
khi nó làm mới lại để hiển thị các lớp dữ<br />
liệu thay đổi.<br />
Một biến thể cải tiến của MVC là mẫu<br />
Hierarchical Model View Controller (HMVC)<br />
[7]. Bên phía client, mô hình HMVC sẽ phân<br />
tầng client vào cấu trúc phân cấp cha – con<br />
(parent-child MVC) cho phép thiết kế hữu<br />
hiệu các tầng kiến trúc của client.<br />
Layer 1<br />
Controller<br />
<br />
Model<br />
<br />
View<br />
<br />
Layer<br />
Controller<br />
<br />
Model<br />
<br />
View<br />
<br />
Layer<br />
Controller<br />
<br />
Model<br />
<br />
View<br />
<br />
Hình 5: Mẫu Strateggy<br />
<br />
Hình 6: Mẫu HMVC<br />
<br />
Trong những hệ thống phân tán có kết nối tới<br />
cơ sở dữ liệu lớn, để hệ thống tối ưu về tốc độ<br />
thì thay vì làm việc với nhiều đối tượng cơ sở<br />
<br />
- View: Là nơi diễn ra tương tác. Trong tương<br />
tác, view liên kết với controller để đưa ra một<br />
sự kiện.<br />
<br />
76<br />
<br />
Ngô Thị Lan và Đtg<br />
<br />
Tạp chí KHOA HỌC & CÔNG NGHỆ<br />
<br />
- Controller: Có một Parent-child hierarchy.<br />
Trong một tầng có một cotroller. Trong tầng<br />
trên nhất, đối tượng controller sẽ truyền sự<br />
kiện xuống hệ thống phân cấp. Khi sự kiện<br />
truyền đến bộ điều khiển cần xử lý nó có thể<br />
hoặc không truyền tiếp.<br />
- Model: Điều khiển thay đổi mô hình khi nó<br />
nhận được một sự kiện yêu cầu cập nhập dữ<br />
liệu. Nếu mô hình thay đổi, nó sẽ thay đổi<br />
trạng thái và thông báo cho view. Thành phần<br />
view lắng nghe sự kiện và thay đổi theo.<br />
Bên phía server, có đối tượng điều khiển mức<br />
trên riêng. Tất cả các yêu cầu được đưa lên bộ<br />
điều khiển cấp cao nhất này. Khi yêu cầu<br />
được nhận, dữ liệu được lấy từ chuỗi đầu vào.<br />
Để không vượt ra ngoài phạm vi nghiên cứu<br />
trong bài báo này, chúng tôi giả sử rằng các<br />
máy chủ biết được định dạng dữ liệu được<br />
chấp nhận bên phía client. Các dữ liệu cần<br />
phải được đưa tới đúng thành phần. Dữ liệu<br />
được chuyển thành các sự kiện và truyền<br />
xuống các controller dưới trong cây phân cấp<br />
của mẫu HMVC. Khi thông tin được chuyển<br />
đến đúng thành phần nhận, nó sẽ thực thi<br />
hành động của yêu cầu, trả kết quả về cho<br />
Controller gốc. Điều khiển của Controller gốc<br />
sẽ đưa kết quả ra theo đúng định dạng chấp<br />
nhận của client.<br />
THẢO LUẬN<br />
Chúng tôi đã nghiên cứu, tổng hợp, đưa ra các<br />
vấn đề cơ bản trong xử lý phân tán và cách áp<br />
dụng mẫu thiết kế vào để thiết kế hệ thống<br />
phân tán sao cho hệ thống dễ dàng thay đổi<br />
mở rộng. Nghiên cứu của chúng tôi là nền<br />
tảng cơ sở ban đầu để xây dụng ứng dụng<br />
thực tế. Hiện chúng tôi đã áp dụng để xây<br />
dựng hệ thống phân tán: Hệ thống quản lịch<br />
cá nhân của giảng viên trường CNTT & TT –<br />
Đại học Thái Nguyên. Do chương trình cần<br />
thời gian để chạy thử nên chúng tôi xin trình<br />
bày kết quả thử nghiệm của mình trong<br />
nghiên cứu tiếp theo.<br />
<br />
99(11): 73 - 78<br />
<br />
TÀI LIỆU THAM KHẢO<br />
[1]. Alan H. Karp, Kevin Smathers, Three Design<br />
Patterns for Secure Distributed Systems, HP<br />
Laboratories Palo Alto, HPL-2003-40, February<br />
25th, 2003<br />
[2]. Ant´onio Rito Silva1, Francisco Assis Rosa2,<br />
Teresa Gonc¸alves2 and Miguel Antunes1,<br />
Distributed Proxy:A Design Pattern for the<br />
Incremental<br />
Development<br />
of<br />
Distributed<br />
Applications, 2000<br />
[http://citeseerx.ist.psu.edu/viewdoc/summary?doi<br />
=10.1.1.32.7664]<br />
[3]. DONG T. B. Thuy and TRAN D. Thu, User<br />
Interface Design by Applying Object – Oriented<br />
Design Patterns, Addendum Contributions to the<br />
4th IEEE International Conference on Computer<br />
Sciences Research, Innovation & Vision for the<br />
Future, February 12-16, Hochiminh City,<br />
Vietnam, 2006.<br />
[4]. Gamma, Erich; Richard Helm, Ralph Johnson,<br />
and John Vlissides (1995). Design Patterns:<br />
Elements of Reusable Object-Oriented Software,<br />
hardcover, 395 pages, Addison-Wesley. ISBN 0201-63361-2.<br />
[5]. George Coulouris, Jean Dillimore and Tim<br />
Kindberg, Distributed Systems: Concepts and<br />
Design, Edition 4, Addison Wesley 2005.<br />
[6]. HMVC: The layered pattern for developing<br />
strong client tiers<br />
[http://www.javaworld.com/javaworld/jw-072000/jw-0721-hmvc.html]<br />
[7]. Karli Kirsimäe, Classical Design Patterns in<br />
Distributed Computing, Research Paper, University<br />
Tartu of mathematic and ìnormatics, 2008.<br />
[8]. Nguyễn Quý Minh, Tăng Nguyễn Trung Hiếu,<br />
Phạm Anh Vũ, Lê Hải Dương, Phương Lan, Design<br />
Patterns. Nhà xuất bản Phương Đông, 2005<br />
[9]. Observer (Java 2 Platform SE v 1.4.2)<br />
[http://java.sun.com/j2se/1.4.2/docs/api/java/util/O<br />
bserver.html]<br />
[10]. Trương Đình Huy, Võ Trung Hùng, Ứng<br />
dụng mẫu thiết kế trong quá trình phát triển phần<br />
mềm, Tạp chí khoa học và công nghệ Đà Nẵng, số<br />
3(38), 2010.<br />
<br />
77<br />
<br />