Cấu trúc lập trình và Mảng
- 16-11-2023
- Toanngo92
- 0 Comments
Cấu trúc giúp xây dựng luồng của một chương trình. Các cấu trúc điều kiện và vòng lặp được sử dụng để thực hiện các hành động cụ thể tùy thuộc vào việc một điều kiện nhất định được thoả mãn hay không. Trong ngôn ngữ lập trình C#, bạn có thể kiểm soát luồng của chương trình bằng các cấu trúc này. Một mảng là một tập hợp các giá trị cùng một loại dữ liệu. Các giá trị này được truy cập bằng một nguồn nhận dạng chung. Buổi học này cung cấp tổng quan về mảng trong C#, bao gồm các loại khác nhau của mảng và mô tả ngắn gọn về chức năng của lớp Mảng. Trong buổi học này, bạn sẽ học được:
- Giải thích về cấu trúc lựa chọn
- Mô tả về cấu trúc vòng lặp
- Giải thích các lệnh nhảy trong C#
- Định nghĩa và mô tả về mảng
- Liệt kê và giải thích các loại mảng
- Giải thích về lớp Mảng
Mục lục
Cấu Trúc Lựa Chọn
Cấu trúc lựa chọn là một cấu trúc lập trình được hỗ trợ bởi C# để kiểm soát luồng của một chương trình. Nó thực thi một khối câu lệnh cụ thể dựa trên một điều kiện boolean, một biểu thức trả về true hoặc false. Các cấu trúc lựa chọn được gọi là các cấu trúc ra quyết định. Do đó, các cấu trúc lựa chọn cho phép bạn đưa ra các quyết định logic về việc thực thi các khối khác nhau trong chương trình để đạt được kết quả logic cần thiết. C# hỗ trợ các cấu trúc ra quyết định sau đây:
- if…else
- if…else..if
- Nested if
- switch…case
Câu Lệnh if
Câu lệnh if cho phép bạn thực thi một khối câu lệnh sau khi đánh giá điều kiện logic cụ thể. Câu lệnh if bắt đầu với từ khóa if và tiếp theo là điều kiện. Nếu điều kiện đánh giá về true, khối câu lệnh theo câu lệnh if sẽ được thực thi. Nếu điều kiện đánh giá về false, khối câu lệnh theo câu lệnh if sẽ bị bỏ qua và các câu lệnh sau khối sẽ được thực thi.
Dưới đây là cú pháp cho câu lệnh if:
if (condition)
{
// one or more statements
}
Trong đó,
- condition: Là biểu thức boolean.
- statements: Là một tập hợp các hướng dẫn thực thi khi biểu thức boolean trả về true.
Hình bên dưới hiển thị một ví dụ về cấu trúc if.
Đoạn mã bên dưới hiển thị xem số đó có là số âm hay không bằng câu lệnh if.
int num = -47;
if (num < 0)
{
Console.WriteLine("The number is negative");
}
Trong Đoạn mã trên, biến num được khai báo là một biến số nguyên và được khởi tạo với giá trị -47. Câu lệnh if được thực thi và giá trị của num được kiểm tra để xem nó có nhỏ hơn 0 hay không. Điều kiện được đánh giá là đúng và đoạn mã “The number is negative” được hiển thị trên cửa sổ console.
Ghi chú: Nếu câu lệnh if chỉ đi sau một câu lệnh duy nhất, việc bao bọc trong dấu ngoặc nhọn {} không cần thiết.
Cấu Trúc if…else
Câu lệnh if chỉ thực thi một khối lệnh chỉ khi điều kiện được chỉ định là true. Tuy nhiên, trong một số tình huống, có thể cần định nghĩa một hành động cho điều kiện false. Điều này được thực hiện bằng cách sử dụng cấu trúc if…else.
Cấu trúc if…else bắt đầu bằng khối lệnh if, tiếp theo là khối lệnh else. Khối lệnh else bắt đầu bằng từ khóa else, sau đó là một khối lệnh. Nếu điều kiện được chỉ định trong câu lệnh if đánh giá về false, các câu lệnh trong khối lệnh else sẽ được thực thi.
Dưới đây là cú pháp cho câu lệnh if…else:
if (điều kiện)
{
// one or more statement
}
else
{
// one or more statement
}
Hình bên dưới thể hiện cấu trúc if…else với một ví dụ.
Đoạn mã bên dưới hiển thị xem một số có là số dương hay số âm bằng cách sử dụng cấu trúc if…else.
int num = 10;
if (num < 0)
{
Console.WriteLine("The number is negative");
}
else
{
Console.WriteLine("The number is positive");
}
Trong Đoạn mã bên trên, num được khai báo là một biến số nguyên và được khởi tạo giá trị là 10. Câu lệnh if được thực thi và giá trị của num được kiểm tra xem có nhỏ hơn 0 hay không. Điều kiện đánh giá là sai và quyền điều khiển của chương trình được chuyển đến khối else và đầu ra “The number is positive” được hiển thị trong cửa sổ console.
Kết quả:
The number is positive
Cấu trúc if…else if
Cấu trúc if…else if cho phép bạn kiểm tra nhiều điều kiện và thực thi một khối mã khác nhau cho mỗi điều kiện. Cấu trúc này còn được gọi là thang máy if-else if. Cấu trúc bắt đầu bằng lệnh if theo sau là nhiều lệnh else if và cuối cùng là một khối else tùy chọn.
Các điều kiện được chỉ định trong cấu trúc if, else if được đánh giá tuần tự. Việc thực thi bắt đầu từ lệnh if đầu tiên. Nếu một điều kiện đánh giá là sai, điều kiện được chỉ định trong lệnh else… if tiếp theo sẽ được đánh giá.
Dưới đây là cú pháp cho cấu trúc if…else if:
if (condition)
{
//one or more statement
}
else if (condition)
{
//one or more statement
}
else
{
//one or more statement
}
Hình ảnh minh họa: Cấu trúc if-else-if
Đoạn mã bên dưới hiển thị xem một số có âm hay không, thậm chí còn sử dụng cấu trúc if else… if.
int num = 13;
if (num < 0)
{
Console.WriteLine("The number is negative");
}
else if (num % 2 == 0)
{
Console.WriteLine("The number is even");
}
else
{
Console.WriteLine("The number is odd");
}
Trong Đoạn mã bên trên, biến num được khai báo là một biến số nguyên và được khởi tạo giá trị là 13. Câu lệnh if được thực thi và giá trị của num được kiểm tra xem có nhỏ hơn 0 không. Điều kiện được đánh giá là sai và quyền điều khiển của chương trình được chuyển đến khối else if. Giá trị của num được chia cho 2 và phần dư được kiểm tra xem có bằng 0 không. Điều kiện này cũng được đánh giá là sai và quyền điều khiển chuyển đến khối else. Cuối cùng, đầu ra “The number is odd” được hiển thị trên cửa sổ console.
Kết quả
The number is odd
Cấu trúc if lồng nhau
Cấu trúc if lồng nhau bao gồm nhiều câu lệnh if. Cấu trúc if lồng nhau bắt đầu với câu lệnh if bên ngoài, được gọi là câu lệnh if ngoài, và chứa nhiều câu lệnh if bên trong, được gọi là câu lệnh if trong.
Trong cấu trúc if lồng nhau, điều kiện if bên ngoài kiểm soát việc thực thi của các câu lệnh if bên trong. Trình biên dịch chỉ thực thi các câu lệnh if bên trong khi điều kiện trong câu lệnh if bên ngoài là đúng. Ngoài ra, mỗi câu lệnh if bên trong chỉ được thực thi nếu điều kiện trong câu lệnh if bên trong trước đó là đúng.
Dưới đây là cú pháp cho cấu trúc if lồng nhau:
if (condition)
{
// one or more statement
if (condition)
{
//one or more statement
}
if (condition)
{
//one or more statement
}
}
Hình bên dưới hiển thị cấu trúc if lồng nhau
Đoạn mã bên dưới hiển thị số tiền thưởng bằng cách sử dụng cấu trúc if lồng nhau
int yrsOfService = 3;
double salary = 1500;
int bonus = 0;
if (yrsOfService < 5)
{
if (salary < 500)
{
bonus = 100;
}
else
{
bonus = 200;
}
}
else
{
bonus = 700;
}
Console.WriteLine("Bonus amount: " + bonus);
Trong Đoạn mã 4, yrsOfService và bonus được khai báo là các biến số nguyên và được khởi tạo giá trị là 3 và 0 tương ứng. Ngoài ra, salary được khai báo là một biến kiểu double và được khởi tạo giá trị là 1500. Lệnh if đầu tiên được thực thi và giá trị của yrs0fService được kiểm tra xem có nhỏ hơn 5 không. Điều kiện này được xác định là đúng. Tiếp theo, giá trị của salary được kiểm tra xem có nhỏ hơn 500 không. Điều kiện này được xác định là sai. Do đó, quyền điều khiển được chuyển đến khối lệnh else của lệnh if trong. Cuối cùng, số tiền thưởng được hiển thị là 200.
Kết quả:
Bonus amount: 200
Cấu trúc switch…case
Một chương trình trở nên khó hiểu khi có quá nhiều câu lệnh if đại diện cho các cấu trúc lựa chọn đa dạng. Để tránh việc sử dụng nhiều câu lệnh if, trong một số trường hợp, phương pháp switch…case có thể được sử dụng như một phương án thay thế.
Lệnh switch…case được sử dụng khi một biến cần được so sánh với các giá trị khác nhau.
- switch
Từ khóa switch được theo sau bởi một biểu thức số nguyên được bao quanh bởi dấu ngoặc đơn. Biểu thức này phải là kiểu int, char, byte hoặc short. Lệnh switch thực thi các trường hợp (case) tương ứng với giá trị của biểu thức.
- case
Từ khóa case được theo sau bởi một hằng số số nguyên duy nhất và một dấu hai chấm. Do đó, lệnh case không thể chứa một biến. Khối mã sau một trường hợp cụ thể được thực thi khi giá trị của biểu thức switch và giá trị của case khớp nhau. Mỗi khối case phải kết thúc bằng từ khóa break để chuyển quyền điều khiển ra khỏi cấu trúc switch.
- default
Nếu không có trường hợp nào khớp với giá trị của biểu thức switch, quyền điều khiển của chương trình được chuyển đến khối mã mặc định (default). Điều này tương đương với khối mã của câu lệnh if…else.
- break
Câu lệnh break là tùy chọn và được sử dụng trong câu lệnh switch…case để kết thúc việc thực hiện chuỗi câu lệnh. Việc điều khiển sẽ được chuyển đến câu lệnh sau khi kết thúc switch. Nếu không có break, việc thực thi sẽ tiếp tục vào câu lệnh case tiếp theo một cách tuần tự. Đôi khi, có thể có nhiều trường hợp mà không có câu lệnh break giữa chúng.
Đoạn mã bên dưới hiển thị ngày của tuần bằng cách sử dụng cấu trúc switch…case.
int day = 5;
switch (day) {
case 1:
Console.WriteLine("Sunday");
break;
case 2:
Console.WriteLine("Monday");
break;
case 3:
Console.WriteLine("Tuesday");
break;
case 4:
Console.WriteLine("Wednesday");
break;
case 5:
Console.WriteLine("Thursday");
break;
case 6:
Console.WriteLine("Friday");
break;
case 7:
Console.WriteLine("Saturday");
break;
default:
Console.WriteLine("Enter a number between 1 to 7");
break;
}
Kết quả:
Thursday
Cấu trúc switch…case lồng nhau
Cấu trúc switch…case cho phép lồng nhau. Điều này có nghĩa là khối case của một cấu trúc switch…case có thể chứa một cấu trúc switch…case khác. Ngoài ra, các hằng số case của cấu trúc switch…case nội bộ có thể có giá trị giống với các hằng số case của cấu trúc bên ngoài.
Đoạn mã bên dưới minh họa việc sử dụng cấu trúc switch lồng nhau.
using System;
class MathOperations {
static void Main(string[] args) {
int numOne;
int numTwo;
int result = 0;
Console.WriteLine("(1) Cộng");
Console.WriteLine("(2) Trừ");
Console.WriteLine("(3) Nhân");
Console.WriteLine("(4) Chia");
int input = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Nhập giá trị thứ nhất");
numOne = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Nhập giá trị thứ hai");
numTwo = Convert.ToInt32(Console.ReadLine());
switch (input) {
case 1:
result = numOne + numTwo;
break;
case 2:
result = numOne - numTwo;
break;
case 3:
result = numOne * numTwo;
break;
case 4:
Console.WriteLine("Bạn muốn tính phần nguyên hay phần dư?");
Console.WriteLine("(1) Phần nguyên");
Console.WriteLine("(2) Phần dư");
int choice = Convert.ToInt32(Console.ReadLine());
switch (choice) {
case 1:
result = numOne / numTwo;
break;
case 2:
result = numOne % numTwo;
break;
default:
Console.WriteLine("Lựa chọn không đúng");
break;
}
break;
default:
Console.WriteLine("Lựa chọn không đúng");
break;
}
Console.WriteLine("Kết quả: " + result);
}
}
Trong Đoạn mã trên, người dùng được yêu cầu chọn phép tính toán mong muốn. Người dùng sau đó nhập các số mà phép tính sẽ được thực hiện. Sử dụng cấu trúc switch..case, dựa trên đầu vào từ người dùng, phép tính phù hợp được thực hiện.
Khối case cho tùy chọn chia sẽ sử dụng một cấu trúc switch..case nằm trong để tính toán phần nguyên hoặc phần dư của phép chia theo lựa chọn được chọn bởi người dùng.
Hình ảnh bên dưới hiển thị kết quả của việc lồng nhau các câu lệnh switch.
Quy tắc không cho phép rơi vào (No-Fall-Through Rule)
Các ngôn ngữ như C, C++, và Java cho phép việc thực thi câu lệnh liên quan đến một case có thể tiếp tục vào case tiếp theo. Việc này được gọi là “falling through”. Tuy nhiên, trong C#, luồng thực thi từ một câu lệnh không được phép tiếp tục đến câu lệnh tiếp theo. Điều này được gọi là “quy tắc không cho phép rơi vào” của C#. Do đó, danh sách các câu lệnh bên trong một khối thường kết thúc bằng một câu lệnh break hoặc goto, gây ra việc điều khiển của chương trình thoát khỏi cấu trúc switch và đi đến câu lệnh tiếp theo sau cấu trúc đó. Khối case cuối cùng (hoặc khối default) cũng phải có một câu lệnh break hoặc goto để rõ ràng đưa điều khiển ra khỏi cấu trúc switch.
C# đã giới thiệu quy tắc không cho phép rơi vào để cho phép trình biên dịch sắp xếp lại thứ tự các khối case để tối ưu hóa hiệu suất. Ngoài ra, quy tắc này ngăn ngừa việc các câu lệnh từ một case tiếp tục vào case khác do lỗi của người lập trình. Mặc dù C# không cho phép chuỗi câu lệnh của một khối case rơi vào case tiếp theo, nhưng nó cho phép các khối case trống (không chứa bất kỳ câu lệnh nào) rơi vào. Do đó, nhiều câu lệnh case có thể được thực thi với cùng một chuỗi mã, như được thể hiện trong đoạn mã bên dưới
using System;
class Months {
static void Main(string[] args) {
string input;
Console.WriteLine("Nhập tháng của bạn: ");
input = Console.ReadLine().ToUpper();
switch(input) {
case "JANUARY":
case "MARCH":
case "MAY":
case "JULY":
case "AUGUST":
case "OCTOBER":
case "DECEMBER":
Console.WriteLine("Tháng này có 31 ngày");
break;
case "APRIL":
case "JUNE":
case "SEPTEMBER":
case "NOVEMBER":
Console.WriteLine("Tháng này có 30 ngày");
break;
case "FEBRUARY":
Console.WriteLine("Tháng này có 28 ngày trong năm không nhuận và 29 ngày trong năm nhuận");
break;
default:
Console.WriteLine("Lựa chọn không hợp lệ");
break;
}
}
}
Trong đoạn mã bên trên, cấu trúc switch..case được sử dụng để hiển thị số ngày trong một tháng cụ thể. Ở đây, tất cả các tháng có 31 ngày được xếp chồng lên nhau để thực thi cùng một câu lệnh. Tương tự, tất cả các tháng có 30 ngày cũng được xếp chồng lên nhau để thực thi cùng một câu lệnh. Ở đây, quy tắc không cho phép rơi vào không bị vi phạm vì các câu lệnh case xếp chồng lên nhau thực thi cùng một mã lệnh. Việc xếp chồng các câu lệnh case giúp tránh sự lặp lại không cần thiết của mã lệnh. Hình bên dưới thể hiện kết quả của việc sử dụng nhiều câu lệnh case.
Vòng lặp cho phép bạn thực thi một câu lệnh đơn hoặc một khối lệnh lặp đi lặp lại. Các ứng dụng phổ biến nhất của vòng lặp bao gồm hiển thị một chuỗi số và lấy đầu vào lặp đi lặp lại. Trong lập trình phần mềm, một cấu trúc vòng lặp chứa một điều kiện giúp trình biên dịch xác định số lần một khối cụ thể sẽ được thực thi. Nếu không có điều kiện, vòng lặp sẽ tiếp tục vô hạn và được gọi là vòng lặp vô hạn. Các cấu trúc vòng lặp cũng được gọi là các câu lệnh lặp lại.
C# hỗ trợ bốn loại cấu trúc vòng lặp. Các loại này bao gồm:
- Vòng lặp while
- Vòng lặp do…while
- Vòng lặp for
- Vòng lặp foreach
Vòng lặp while
Vòng lặp while được sử dụng để thực thi một khối mã lặp đi lặp lại miễn là điều kiện của vòng lặp vẫn đúng. Vòng lặp while bao gồm câu lệnh while, bắt đầu bằng từ khóa while và tiếp theo là một điều kiện boolean. Nếu điều kiện đánh giá thành true, khối lệnh sau câu lệnh while được thực thi.
Sau mỗi lần lặp, điều khiển được chuyển trở lại câu lệnh while và điều kiện được kiểm tra lại để thực hiện vòng lặp tiếp theo. Khi điều kiện được đánh giá là false, khối lệnh sau câu lệnh while bị bỏ qua và câu lệnh xuất hiện sau khối lệnh đó được thực thi bởi trình biên dịch.
Dưới đây là cú pháp của vòng lặp while:
while (condition)
{
// one or more statements
}
Trong đó,
- condition: Xác định biểu thức boolean.
Hình bên dưới thể hiện vòng lặp while.
Đoạn mã bên dưới hiển thị các số chẵn từ 1 đến 10 bằng vòng lặp while
public int num = 1;
Console.WriteLine("Các số chẵn");
while (num <= 10)
{
if (num % 2 == 0)
{
Console.WriteLine(num);
}
num++;
}
Trong Đoạn mã trên, biến num được khai báo là một biến số nguyên và khởi tạo giá trị là 1. Điều kiện trong vòng lặp while được kiểm tra, chỉ định rằng giá trị của biến num phải nhỏ hơn hoặc bằng 11. Nếu điều kiện này là đúng, giá trị của biến num được chia cho 2 và phần dư được kiểm tra xem có bằng 0 không. Nếu phần dư là 0, giá trị của biến num được hiển thị trong cửa sổ console và biến num được tăng lên 1. Sau đó, điều khiển chương trình được chuyển đến câu lệnh while để kiểm tra điều kiện một lần nữa. Khi giá trị của num trở thành 12, vòng lặp while kết thúc vì điều kiện vòng lặp trở thành sai.
Kết quả:
Event Numbers
2
4
6
8
10
Ghi chú: Điều kiện cho vòng lặp while luôn được kiểm tra trước khi thực thi vòng lặp. Do đó, vòng lặp while còn được gọi là vòng lặp kiểm tra trước (pre-test loop).
Vòng lặp while lồng nhau
Vòng lặp while có thể được tạo bên trong một vòng lặp while khác để tạo ra một cấu trúc vòng lặp while lồng nhau. Đoạn mã bên dưới minh họa việc sử dụng vòng lặp while lồng nhau để tạo ra một mẫu hình học.
using System;
class Pattern {
static void Main(string[] args) {
int i = 0;
while (i < 5) {
int j = 0;
while (j < i + 1) {
Console.Write("*");
j++;
}
Console.WriteLine();
i++;
}
}
}
Trong Đoạn mã bên trên, một mẫu của tam giác vuông góc được tạo ra bằng ký tự (*) asterisk. Điều này được thực hiện bằng cách sử dụng vòng lặp while lồng nhau.
Hình bên dưới thể hiện kết quả của việc sử dụng vòng lặp while lồng nhau.
Vòng lặp này tương tự như vòng lặp while, tuy nhiên, nó luôn được thực thi ít nhất một lần mà không kiểm tra điều kiện. Vòng lặp bắt đầu với từ khóa ‘do’ và tiếp theo là một khối lệnh có thể thực thi. Câu lệnh ‘while’ cùng với điều kiện xuất hiện ở cuối khối lệnh này.
Các câu lệnh trong vòng lặp ‘do-while’ được thực thi miễn là điều kiện được chỉ định vẫn là đúng. Khi điều kiện đánh giá là sai, các khối lệnh sau từ khóa ‘do’ sẽ bị bỏ qua và câu lệnh ngay sau câu lệnh ‘while’ sẽ được thực thi.
Dưới đây là cú pháp của vòng lặp ‘do-while’:
do
{
//one or more statements
} while (condition);
Hình bên dưới hiển thị vòng lặp do…while
Đoạn mã bên dưới hiển thị các số chẵn từ 1 đến 10 bằng vòng lặp do-while
int num = 1;
Console.WriteLine("Các số chẵn");
do
{
if (num % 2 == 0)
{
Console.WriteLine(num);
}
num = num + 1;
} while (num <= 10);
Trong đoạn mã trên, biến num được khai báo là một biến số nguyên và được khởi tạo giá trị là 1. Trong khối lệnh do, mà không kiểm tra bất kỳ điều kiện nào, giá trị của num được chia cho 2 và phần dư được kiểm tra xem có bằng 0 không. Nếu phần dư là 0, giá trị của num được hiển thị và sau đó num được tăng thêm 1.
Tiếp theo, điều kiện trong câu lệnh while được kiểm tra để xem giá trị của num có nhỏ hơn hoặc bằng 11 hay không. Nếu điều kiện này đúng, vòng lặp do-while sẽ được thực thi lại. Khi giá trị của num trở thành 12, vòng lặp do-while kết thúc.
Kết quả:
Các số chẵn:
2
4
6
8
10
Ghi chú: Các câu lệnh được định nghĩa trong vòng lặp do-while được thực thi lần đầu tiên và sau đó điều kiện cụ thể được kiểm tra. Do đó, vòng lặp do-while được gọi là vòng lặp kiểm tra sau (post-test loop).
Vòng lặp for
Câu lệnh for tương tự như câu lệnh while trong chức năng của nó. Các câu lệnh bên trong thân của vòng lặp được thực thi miễn là điều kiện là đúng. Ở đây, điều kiện cũng được kiểm tra trước khi các câu lệnh được thực thi.
Dưới đây là cú pháp của vòng lặp for:
for (initialization; condition; increment/decrement)
{
// one or more statement
}
trong đó,
- initialization: Khởi tạo biến sẽ được sử dụng trong điều kiện.
- condition: Bao gồm điều kiện được kiểm tra trước khi các câu lệnh trong vòng lặp được thực thi.
- increment/decrement: Bao gồm câu lệnh thay đổi giá trị của biến để đảm bảo rằng điều kiện được chỉ định trong phần điều kiện được đạt được. Thông thường, các toán tử tăng và giảm như ++, — và các toán tử viết tắt như += hoặc -= được sử dụng trong phần này. Lưu ý rằng không có dấu chấm phẩy ở cuối các biểu thức tăng/giảm.
Hình bên dưới hiển thị vòng lặp for
Đoạn mã bên dưới hiển thị các số chẵn từ 1 đến 10 bằng vòng lặp for.
Console.WriteLine("Even Numbers");
for (int num = 1; num <= 11; num++) {
if (num % 2 == 0) {
Console.WriteLine(num);
}
}
Trong đoạn mã trên, biến num được khai báo là một biến số nguyên và nó được khởi tạo giá trị là 1 trong câu lệnh for. Điều kiện được chỉ định trong câu lệnh for được kiểm tra để giá trị của num có nhỏ hơn hoặc bằng 11 không. Nếu điều kiện này đúng, giá trị của num được chia cho 2 và dư được kiểm tra xem có bằng 0 không. Nếu điều kiện này đúng, quyền điều khiển được chuyển đến câu lệnh For lại. Ở đây, giá trị của num được tăng và điều kiện được kiểm tra lại. Khi giá trị của num trở thành 12, điều kiện của vòng lặp for trở thành sai và vòng lặp kết thúc.
Kết quả:
Even Numbers
2
4
6
8
10
Vòng lặp for lồng nhau
Nested for loops, hay vòng lặp lồng nhau, bao gồm nhiều câu lệnh for. Khi một vòng lặp for được bao quanh bởi một vòng lặp for khác, các vòng lặp được gọi là lồng nhau. Vòng lặp for bao quanh một vòng lặp for khác được gọi là vòng lặp for bên ngoài trong khi vòng lặp for bên trong được gọi là vòng lặp for bên trong. Vòng lặp for bên ngoài xác định số lần vòng lặp for bên trong sẽ được gọi. Đối với mỗi lần lặp của vòng lặp for bên ngoài, vòng lặp for bên trong thực hiện tất cả các lần lặp của nó.
Đoạn mã bên dưới thể hiện một ma trận 2×2 bằng cách sử dụng vòng lặp for lồng nhau.
int rows = 2;
int columns = 2;
for (int i = 0; i < rows; i++) {
for (int j = 0; j < columns; j++) {
Console.Write("{0}", i*j);
}
Console.WriteLine();
}
Trong đoạn mã bên trên, rows và columns được khai báo là các biến số nguyên và được khởi tạo giá trị là 2. Ngoài ra, i và j được khai báo là các biến số nguyên trong vòng lặp For bên ngoài và bên trong tương ứng và cả hai đều được khởi tạo là 0. Khi vòng lặp for bên ngoài được thực thi, giá trị của i được kiểm tra để xem nó có nhỏ hơn 2 hay không. Ở đây, điều kiện là đúng do đó, vòng lặp for bên trong được thực thi. Trong vòng lặp này, giá trị của j được kiểm tra để xem nó có nhỏ hơn 2 hay không. Miễn là nó nhỏ hơn 2, tích của các giá trị của i và j được hiển thị trong cửa sổ console. Vòng lặp for bên trong này thực thi cho đến khi j trở thành lớn hơn hoặc bằng 2, lúc đó, quyền điều khiển chuyển qua vòng lặp For bên ngoài.
Kết quả:
0 0
0 1
Vòng lặp For với nhiều biến điều khiển vòng lặp
Vòng lặp For cho phép sử dụng nhiều biến để điều khiển vòng lặp.
Đoạn mã bên dưới thể hiện việc sử dụng vòng lặp For với hai biến.
using System;
class Numbers {
static void Main(string[] args) {
Console.WriteLine("Square \t\tCube");
for (int i = 1, j = 0; i < 11; i++) {
if ((i % 2) == 0) {
Console.Write("{0} = {1}\t", i, (i*i));
} else {
Console.Write("{0} = {1}\n", j, (j * j * j));
}
}
}
}
Trong đoạn mã trên, phần khởi tạo cũng như phần tăng/giảm của định nghĩa vòng lặp for chứa hai biến i và j. Các biến này được sử dụng trong thân vòng lặp for, để hiển thị bình phương của tất cả các số chẵn, và lập phương của tất cả các số lẻ từ 1 đến 10.
Hình bên dưới mô tả việc sử dụng vòng lặp For.
Định nghĩa của vòng lặp for có thể chia thành ba phần: khởi tạo, điều kiện, và phần tăng/giảm. Điều này cho phép tạo ra vòng lặp for ngay cả khi một hoặc nhiều phần của định nghĩa vòng lặp bị bỏ sót. Thực tế, vòng lặp For có thể được tạo ra mà không có cả ba phần.
Đoạn mã bên dưới thể hiện một vòng lặp for mà bỏ qua hoặc loại bỏ phần tăng/giảm trong định nghĩa của nó.
using System;
class Investment {
static void Main(string[] args) {
int investment = 0;
int returns = 0;
int expenses;
int profit;
int counter = 0;
for (investment=1000; returns=0; returns < investment;) {
Console.WriteLine("Nhập chi phí hàng tháng:");
expenses = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Nhập lợi nhuận hàng tháng:");
profit = Convert.ToInt32(Console.ReadLine());
investment += expenses;
returns += profit;
counter++;
}
Console.WriteLine("Số tháng để vượt qua điểm cân đối: " + counter);
}
}
Trong đoạn mã trên, vòng lặp For được sử dụng để tính toán số tháng mà một doanh nghiệp cần để thu hồi vốn đầu tư và đạt điểm cân đối. Chi phí và lợi nhuận mỗi tháng được nhập từ người dùng và lưu trữ trong biến expenses và profit tương ứng. Tổng số vốn đầu tư được tính bằng tổng của vốn đầu tư ban đầu cộng với chi phí hàng tháng. Tổng lợi nhuận được tính bằng tổng của lợi nhuận từng tháng. Số lần lặp của vòng lặp For được lưu trong biến counter. Biểu thức điều kiện của vòng lặp kết thúc vòng lặp khi tổng lợi nhuận của doanh nghiệp trở nên lớn hơn hoặc bằng tổng vốn đầu tư. Sau đó, mã in ra số tháng mà doanh nghiệp đã mất để đạt điểm cân đối. Số tháng bằng số lần lặp của vòng lặp for vì mỗi lần lặp đại diện cho một tháng mới.
Hình bên dưới mô tả vòng lặp for với phần thiếu trong quá trình thực hiện.
Đoạn mã bên dưới trình bày một vòng lặp for bỏ qua phần khởi tạo cũng như phần tăng/
phần giảm dần của định nghĩa vòng lặp.
int investment = 1000;
int returns = 0;
for (; returns < investment;) {
// for loop statement
}
Trong Đoạn mã trên, việc khởi tạo biến investment và returns được thực hiện trước định nghĩa vòng lặp for. Do đó, vòng lặp đã được định nghĩa với phần khởi tạo để trống.
Nếu phần điều kiện của vòng lặp For bị bỏ sót, vòng lặp trở thành vòng lặp vô hạn. Những vòng lặp như vậy có thể được kết thúc bằng cách sử dụng câu lệnh nhảy như break hoặc goto để thoát khỏi vòng lặp.
Đoạn mã bên dưới thể hiện việc sử dụng một vòng lặp for vô hạn.
using System;
class Summation {
static void Main(string[] args) {
char c;
int numOne;
int numTwo;
int result;
for (;;) {
Console.WriteLine("Nhập số thứ nhất:");
numOne = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("Nhập số thứ hai:");
numTwo = Convert.ToInt32(Console.ReadLine());
result = numOne + numTwo;
Console.WriteLine("Kết quả của phép cộng: " + result);
Console.WriteLine("Bạn có muốn tiếp tục [Y/N] ?");
c = Convert.ToChar(Console.ReadLine());
if (c == 'Y' || c == 'y') {
continue;
}
else {
break;
}
}
}
}
Trong đoạn mã trên, một vòng lặp for vô hạn được sử dụng để lặp lại việc nhập hai số từ người dùng. Hai số này được cộng lại và kết quả được in ra trên cửa sổ console. Sau mỗi lần lặp của vòng lặp, câu lệnh if được sử dụng để kiểm tra liệu người dùng muốn tiếp tục hay không.
Nếu câu trả lời là ‘Y’ hoặc ‘y’ (biểu thị cho có), vòng lặp sẽ được thực thi lại, ngược lại vòng lặp sẽ được thoát bằng câu lệnh break.
Hình bên dưới mô tả việc sử dụng vòng lặp for vô hạn.
Vòng lặp for không có phần thân
Trong C#, một vòng lặp For có thể được tạo mà không có phần thân. Loại vòng lặp này xảy ra khi tất cả các hoạt động cần thực hiện trong phạm vi của vòng lặp có thể được chứa trong định nghĩa của vòng lặp.
Đoạn mã bên dưới minh họa việc sử dụng một vòng lặp For không có phần thân.
using System;
class Factorial {
static void Main(string[] args) {
int fact = 1;
int num, i;
Console.WriteLine("Nhập số để tính giai thừa");
num = Convert.ToInt32(Console.ReadLine());
for (int i = 1; i <= num; fact *= i++) ;
Console.WriteLine("Giai thừa: " + fact);
}
}
Trong đoạn mã trên, quá trình tính giai thừa của một số được người dùng nhập được thực hiện hoàn toàn trong định nghĩa của vòng lặp, vòng lặp không có phần thân.
Hình bên dưới mô tả kết quả sử dụng một vòng lặp for không có phần thân.
Khai báo Biến kiểm soát vòng lặp trong định nghĩa vòng lặp for
Các biến kiểm soát vòng lặp thường được tạo ra cho các vòng lặp như vòng lặp for. Một khi vòng lặp kết thúc, không còn sử dụng nữa các biến này. Trong những trường hợp như vậy, các biến này có thể được tạo ra trong phần khởi tạo của định nghĩa vòng lặp for.
Dưới đây là cú pháp để khai báo biến kiểm soát vòng lặp trong định nghĩa vòng lặp:
for (int i = 1; i <= num; fact *= i++)
{
// some statements
}
foreach (<datatype> <identifier> in <list>)
{
// one or more statement
}
trong đó,
<datatype>: Xác định kiểu dữ liệu của các phần tử trong danh sách.
<identifier>: Là một tên phù hợp cho bộ sưu tập các phần tử.
<list>: Xác định tên của danh sách.
Đoạn mã bên dưới hiển thị tên của nhân viên bằng vòng lặp foreach.
string[] employeeNames = { "Maria", "Wilson", "Elton", "Garry" };
Console.WriteLine("Danh sách Tên Nhân Viên:");
foreach (string names in employeeNames)
{
Console.WriteLine("{0}", names);
}
Trong đoạn mã trên, danh sách tên nhân viên được khai báo trong một mảng các biến chuỗi gọi là employeeNames. Trong câu lệnh foreach, kiểu dữ liệu được khai báo là string và tên biến được chỉ định là names. Biến này tham chiếu đến tất cả các giá trị từ mảng employeeNames. Vòng lặp foreach hiển thị tên của các nhân viên theo thứ tự mà chúng được lưu trữ trong mảng.
Các lệnh nhảy trong C#
Các lệnh nhảy được sử dụng để chuyển quyền điều khiển từ một điểm trong chương trình đến một điểm khác. Sẽ có những tình huống khi bạn cần phải thoát ra khỏi một vòng lặp sớm và tiếp tục với chương trình.
Trong những trường hợp như vậy, các lệnh nhảy được sử dụng. Lệnh nhảy chuyển quyền điều khiển của chương trình tới một vị trí khác một cách không điều kiện. Vị trí mà một lệnh nhảy chuyển quyền điều khiển được gọi là đích của lệnh nhảy.
C# hỗ trợ bốn loại lệnh nhảy. Chúng là:
- break
- continue
- goto
- return
Lệnh break
Lệnh break được sử dụng trong các cấu trúc lựa chọn và vòng lặp. Nó được sử dụng rộng rãi nhất trong cấu trúc switch…case và trong các vòng lặp for và while. Lệnh break được biểu thị bằng từ khóa break. Trong cấu trúc switch…case, nó được sử dụng để kết thúc việc thực thi của cấu trúc đó. Trong vòng lặp, nó được sử dụng để thoát ra khỏi vòng lặp mà không kiểm tra điều kiện của vòng lặp. Trong trường hợp này, quyền điều khiển chuyển đến câu lệnh tiếp theo sau vòng lặp.
Hình bên dưới hiển thị câu lệnh break
Đoạn mã bên dưới hiển thị một số nguyên tố bằng cách sử dụng vòng lặp while và lệnh break
int numOne = 17;
int numTwo = 2;
while (numTwo <= numOne - 1)
{
if (numOne % numTwo == 0)
{
Console.WriteLine("Not a Prime Number");
break;
}
numTwo++;
}
if (numTwo == numOne)
{
Console.WriteLine("Prime Number");
}
Trong Đoạn mã trên, ‘numOne’ và ‘numTwo’ được khai báo là các biến số nguyên và được khởi tạo với giá trị là 17 và 2 tương ứng. Trong câu lệnh while, nếu điều kiện đúng, điều kiện bên trong được kiểm tra. Nếu điều kiện này đánh giá là đúng, quyền điều khiển chương trình chuyển đến câu lệnh if bên ngoài vòng lặp while. Nếu điều kiện là sai, giá trị của ‘numTwo’ được tăng lên và quyền điều khiển chuyển đến câu lệnh while.
Lệnh continue
Lệnh continue được sử dụng phổ biến nhất trong cấu trúc vòng lặp. Lệnh này được biểu thị bằng từ khóa continue. Lệnh continue được sử dụng để kết thúc vòng lặp hiện tại và chuyển quyền điều khiển của chương trình trở lại đầu vòng lặp. Các câu lệnh trong vòng lặp sau lệnh continue sẽ bị bỏ qua trong vòng lặp hiện tại.
Hình bên dưới mô tả lệnh continue.
Đoạn mã bên dưới hiển thị các số chẵn trong khoảng từ 1 đến 10 bằng cách sử dụng vòng lặp for và lệnh continue
Console.WriteLine("Even numbers in the range of 1-10");
for (int i = 1; i <= 10; i++)
{
if (i % 2 != 0)
{
continue;
}
Console.Write(i + " ");
}
Đoạn mã bên trên thực hiện việc khai báo i là một số nguyên và khởi tạo giá trị là 1 trong định nghĩa vòng lặp for. Trong thân vòng lặp, giá trị của i được chia cho 2 và dư của phép chia được kiểm tra xem có bằng 0 không. Nếu dư bằng 0, giá trị của i được hiển thị ra màn hình vì nó là một số chẵn. Nếu dư không bằng 0, lệnh continue được thực thi và quyền điều khiển chương trình chuyển về đầu vòng lặp for.
Kết quả:
Even numbers in the range of 1-10
2 4 6 8 10
Lệnh goto
Lệnh goto cho phép bạn thực thi trực tiếp một câu lệnh có nhãn hoặc một khối câu lệnh có nhãn. Một khối có nhãn hoặc một câu lệnh có nhãn bắt đầu bằng một nhãn. Một nhãn là một định danh kết thúc bằng dấu hai chấm. Một khối có nhãn có thể được tham chiếu bởi nhiều lệnh goto khác nhau.
Câu lệnh goto được biểu thị bằng từ khóa goto. Hình bên dưới hiển thị câu lệnh goto
Đoạn mã bên dưới hiển thị thông điệp “Hello World” năm lần bằng cách sử dụng lệnh goto.
int i = 0;
display:
Console.WriteLine("Hello World");
i++;
if (i < 5)
{
goto display;
}
Trong đoạn mã bên trên, biến i được khai báo là một số nguyên và được khởi tạo giá trị là 0. Quyền điều khiển chương trình được chuyển đến nhãn display và thông điệp “Hello World” được hiển thị. Sau đó, giá trị của i được tăng lên 1 và kiểm tra xem nó có nhỏ hơn 5 không. Nếu điều kiện này đúng, lệnh goto được thực thi và quyền điều khiển của chương trình được chuyển đến nhãn display. Nếu điều kiện này sai, chương trình kết thúc.
Kết quả:
Hello World
Hello World
Hello World
Hello World
Hello World
Đoạn mã bên dưới mô tả việc sử dụng lệnh goto để thoát khỏi một vòng lặp lồng nhau
class Factorial
{
static void Main(string[] args)
{
byte num = 0;
while (true)
{
byte fact = 1;
Console.Write("Please enter a number: ");
num = Convert.ToByte(Console.ReadLine());
if (num < 0)
{
goto stop;
}
for (byte j = num; j > 0; j--)
{
if (j > 4)
{
goto stop;
}
fact *= j;
}
Console.WriteLine("Factorial of {0} is {1}", num, fact);
}
stop:
Console.WriteLine("Exiting the program");
}
}
Đoạn mã này yêu cầu người dùng nhập một số. Nếu số nhập vào nhỏ hơn 0, chương trình sẽ thoát. Nếu số nhập vào lớn hơn 4, vòng lặp sẽ kết thúc. Các giai thừa của các số nhỏ hơn hoặc bằng 4 sẽ được hiển thị.
Hình bên dưới mô tả việc sử dụng lệnh goto. Thường không được khuyến khích vì có thể làm cho mã nguồn trở nên khó hiểu và quản lý hơn.
Lệnh return
Lệnh return được sử dụng để trả về một giá trị của biểu thức hoặc được sử dụng để chuyển quyền điều khiển về phương thức từ đó phương thức hiện tại được gọi. Lệnh return được biểu thị bằng từ khóa return. Lệnh return phải là câu lệnh cuối cùng trong khối của phương thức.
Hình bên dưới mô tả lệnh return. Lệnh này thường được sử dụng để trả về một giá trị từ một phương thức hoặc để kết thúc sự thực thi của phương thức và chuyển quyền điều khiển trở lại nơi phương thức đã được gọi.
Đoạn mã bên dưới hiển thị khối của một số bằng câu lệnh return.
class Program
{
static void Main(string[] args)
{
int num = 23;
Console.WriteLine("Lập phương của {0} = {1}", num, Cube(num));
}
static int Cube(int n)
{
return (n * n * n);
}
}
Đoạn mã bên trên khai báo biến num là một số nguyên và khởi tạo giá trị là 23. Phương thức Cube() được gọi thông qua phương thức Console.WriteLine(). Lúc này, quyền điều khiển của chương trình chuyển đến phương thức Cube(), phương thức này trả về giá trị lập phương của số đã được chỉ định. Lệnh return trả về giá trị lập phương đã tính về phương thức Console.WriteLine(), và sau đó hiển thị giá trị lập phương đã tính của số 23.
Kết quả:
Cube of 23 = 12167
Đoạn mã bên dưới minh họa cách sử dụng câu lệnh return để kết thúc chương trình.
class Factorial
{
static void Main(string[] args)
{
int yrsOfService = 5;
double salary = 1250;
double bonus = 0;
if (yrsOfService <= 5)
{
bonus = 50;
return;
}
else
{
bonus = salary * 0.2;
}
Console.WriteLine("Salary amount: " + salary);
Console.WriteLine("Bonus amount: " + bonus);
}
}
Trong Đoạn mã trên, biến yrsOfService được khai báo là một biến số nguyên và được khởi tạo giá trị là 5. Ngoài ra, salary và bonus được khai báo là kiểu dữ liệu double và được khởi tạo lần lượt với giá trị là 1250 và 0.
Điều kiện yrsOfService <= 5 được kiểm tra và trả về kết quả là đúng vì yrsOfService được đặt là 5 ban đầu. Do đó, biến bonus được gán giá trị là 50.
Tiếp theo, lệnh return được thực thi, chương trình kết thúc ngay lập tức mà không tiến hành thực hiện các lệnh còn lại trong chương trình. Do đó, không có bất kỳ đầu ra nào được hiển thị từ chương trình này.
Giới thiệu về Mảng
Một mảng là một bộ sưu tập các phần tử của cùng một kiểu dữ liệu được lưu trữ tại các vị trí bộ nhớ liền kề nhau. Ví dụ, trong một chương trình, một mảng có thể được định nghĩa để chứa 30 phần tử để lưu trữ điểm số của 30 sinh viên.
Mục đích
Xem xét một chương trình lưu trữ tên của 100 sinh viên. Để lưu trữ các tên này, người lập trình viên sẽ tạo 100 biến kiểu string.
Việc tạo và quản lý 100 biến này là một công việc mất thời gian vì nó dẫn đến việc sử dụng bộ nhớ không hiệu quả. Trong những tình huống như vậy, người lập trình viên có thể tạo một mảng để lưu trữ 100 tên.
Một mảng là một bộ sưu tập các giá trị liên quan được đặt trong các vị trí bộ nhớ liền kề và những giá trị này được tham chiếu bằng một tên mảng chung. Điều này giúp đơn giản hóa việc duy trì những giá trị này.
Hình bên dưới thể hiện một ví dụ để minh họa mục đích của mảng.
Định nghĩa
Một mảng luôn lưu trữ các giá trị của một kiểu dữ liệu duy nhất. Mỗi giá trị được gọi là một phần tử. Các phần tử này được truy cập bằng cách sử dụng chỉ số hoặc số chỉ mục (index) xác định vị trí của phần tử trong danh sách mảng.
C# hỗ trợ các giá trị chỉ số dựa trên zero (zero-based index) trong một mảng. Điều này có nghĩa là phần tử đầu tiên trong mảng có số chỉ mục là 0, trong khi phần tử cuối cùng có số chỉ mục là n-1, trong đó n là tổng số phần tử trong mảng.
Sắp xếp các giá trị này giúp lưu trữ dữ liệu một cách hiệu quả, dễ dàng sắp xếp dữ liệu và dễ dàng theo dõi độ dài của dữ liệu. Hình bên dưới trình bày một ví dụ về các số chỉ mục và phần tử trong một mảng.
Khai báo Mảng
Mảng là các biến kiểu tham chiếu (reference type) có quá trình tạo bao gồm hai bước: khai báo và cấp phát bộ nhớ.
Khai báo một mảng chỉ định kiểu dữ liệu mà mảng có thể chứa cũng như một định danh. Định danh này thực chất là tên mảng và được sử dụng với một chỉ số để lấy hoặc đặt giá trị dữ liệu tại vị trí đó. Việc khai báo một mảng không cấp phát bộ nhớ cho mảng.
Dưới đây là cú pháp cho việc khai báo một mảng:
type[] arrayName;
trong đó,
- type: Xác định kiểu dữ liệu của các phần tử trong mảng (ví dụ: int, double, string…)
- arrayName: Đặt tên cho mảng.
Khởi tạo Mảng
Một mảng có thể được tạo bằng từ khóa new và sau đó được khởi tạo. Hoặc có thể khởi tạo mảng ngay từ lúc khai báo, trong trường hợp đó từ khóa new không được sử dụng. Tạo và khởi tạo một mảng với từ khóa new bao gồm chỉ định kích thước của mảng. Số lượng phần tử được lưu trữ trong một mảng phụ thuộc vào kích thước đã chỉ định. Từ khóa new cấp phát bộ nhớ cho mảng và sau đó có thể gán giá trị cho mảng.
Nếu các phần tử không được gán giá trị một cách rõ ràng, giá trị mặc định sẽ được lưu trữ trong mảng.
Bảng bên dưới liệt kê các giá trị mặc định cho một số kiểu dữ liệu thông dụng.
Kiểu Dữ Liệu | Giá Trị Mặc Định |
int | 0 |
float | 0.0 |
double | 0.0 |
char | ‘\0’ |
string | Null |
Cú pháp sau được sử dụng để tạo một mảng:
arrayName = new type[size-value];
Cú pháp sau được sử dụng để khai báo và tạo một mảng trong cùng một câu lệnh sử dụng từ khóa new:
type[] arrayName = new type[size-value];
trong đó,
- size-value: Xác định số phần tử trong mảng. Bạn có thể chỉ định một biến kiểu int để lưu trữ kích thước của mảng thay vì chỉ định trực tiếp một giá trị.
Sau khi một mảng đã được tạo bằng cách sử dụng cú pháp này, các phần tử của nó có thể được gán giá trị bằng cách sử dụng cả chỉ số hoặc sử dụng một cấu trúc lặp như vòng lặp for.
Cú pháp sau được sử dụng để tạo và khởi tạo một mảng mà không sử dụng từ khóa new:
type[ ] arrayIdentifier(val1, val2, val3, ..., valN);
trong đó,
- val1: là giá trị của phần tử đầu tiên
- valN: là giá trị của phần tử thứ N
Đoạn mã bên dưới tạo một mảng số nguyên có thể chứa tối đa năm phần tử.
public int[] numbers = new int[5];
Đoạn mã bên dưới khởi tạo một mảng kiểu string và gán tên tại các vị trí chỉ mục tương ứng.
string[] studNames = new string[] { "Allan", "Wilson", "James", "Arnold" };
Trong Đoạn mã trên, chuỗi “Allan” được lưu tại chỉ mục 0, “Wilson” tại chỉ mục 1, “James” tại chỉ mục 2 và “Arnold” tại chỉ mục 3.
Đoạn mã bên dưới lưu chuỗi “Jack” là tên của sinh viên thứ năm.
studNames[4] = "Jack";
Đoạn mã bên dưới thể hiện một cách khác để tạo và khởi tạo một mảng. Một mảng có tên là count được tạo và được gán giá trị kiểu int.
using System;
class Numbers {
static void Main(string[] args) {
int[] count = new int[10]; // Mảng được tạo ra
int counter = 0;
for (int i = 0; i < 10; i++) {
count[i] = counter++; // Gán giá trị cho các phần tử
Console.WriteLine("The count value is: " + count[i]); // In ra giá trị của từng phần tử
}
}
}
Trong Đoạn mã bên trên, lớp Numbers khai báo một biến mảng count có kích thước là 10. Một biến int counter được khai báo và gán giá trị là O. Sử dụng vòng lặp For, mỗi phần tử của mảng count được gán giá trị tăng lên của biến counter.
Kết quả:
The count value is: 0
The count value is: 1
The count value is: 2
The count value is: 3
The count value is: 4
The count value is: 5
The count value is: 6
The count value is: 7
The count value is: 8
The count value is: 9
Truy cập trực tiếp đến các phần tử Mảng
Các phần tử của mảng có thể được truy cập bằng chỉ mục. Trong quá trình định nghĩa mảng, người ta phải chỉ định kích thước của mảng. Điều này được thực hiện vì dựa vào kích thước, một mảng sẽ được cấp phát bộ nhớ liên tục dựa trên kích thước đó.
Các phần tử của mảng được gán nhãn tăng dần, bắt đầu từ 0 cho phần tử đầu tiên. Nói cách khác, chỉ số của một phần tử mảng bắt đầu từ giá trị chỉ mục 0. Ví dụ, phần tử thứ bảy của mảng sẽ được đánh chỉ mục là 6, và phần tử thứ ba của mảng sẽ được đánh chỉ mục là 4. Bằng cách sử dụng toán tử dấu ngoặc vuông, một phần tử cụ thể có thể được truy cập bằng cách bao quanh chỉ mục trong dấu ngoặc vuông như được thể hiện trong Đoạn mã bên dưới.
using System;
namespace xyz {
class ElementAccessDemo {
public static void Main() {
int[] scores;
// allocating memory for scores array and initializing the array.
scores = new int[] { 79, 54, 63, 76, 22 };
Console.Write("Third element: ");
Console.Write(scores[2]);
}
}
}
Dưới đây, kết quả sẽ là 63, bởi vì 63 là phần tử thứ ba và được truy cập bằng chỉ mục 2.
Độ dài Mảng trong C#
Thuộc tính Length của một mảng trong C# có thể được sử dụng để lấy số lượng phần tử trong một mảng cụ thể. Đoạn mã bên dưới thể hiện việc sử dụng thuộc tính Length cho các mảng kiểu int và string
using System;
namespace xyz {
class LenDemo {
public static void Main() {
int[] numbers;
// cấp phát bộ nhớ cho mảng numbers
numbers = new int[] {1, 3, 5, 7, 9};
Console.Write("\nTotal Number of Elements in Interger Array: ");
// sử dụng thuộc tính Length
Console.Write(numbers.Length);
string[] animals;
// cấp phát bộ nhớ cho mảng animals
animals = new string[] {"Dog", "Cat", "Rat"};
Console.Write("\nTotal Number of Elements in String Array: ");
// sử dụng thuộc tính Length
Console.Write(animals.Length);
}
}
}
Kết quả của đoạn mã trên sẽ như sau:
Total Number of Elements in Interger Array: 5
Total Number of Elements in String Array: 3
Mảng Một Chiều
Các phần tử của mảng một chiều được lưu trữ trong một hàng duy nhất trong bộ nhớ đã cấp phát. Khai báo và khởi tạo mảng một chiều tương tự như khai báo và khởi tạo mảng tiêu chuẩn.
Trong một mảng một chiều, các phần tử được đánh chỉ mục từ 0 đến (n-1), trong đó n là tổng số phần tử trong mảng. Ví dụ, một mảng có 5 phần tử sẽ có các phần tử được đánh chỉ mục từ 0 đến 4, với phần tử đầu tiên được đánh chỉ mục là 0 và phần tử cuối cùng được đánh chỉ mục là 4.
Cú pháp sau được sử dụng để khai báo và khởi tạo một mảng một chiều:
type[] arrayName; // Khai báo
arrayName = new type[length]; // Khởi tạo
trong đó,
- type: là kiểu biến và được theo sau bởi dấu ngoặc vuông.
- arrayName: là tên của biến.
- length: xác định số lượng phần tử được khai báo trong mảng.
- new: tạo ra mảng.
Đoạn mã bên dưới đây khởi tạo một mảng một chiều để lưu trữ tên của sinh viên.
using System;
class SingleDimensionArray {
static void Main(string[] args) {
string[] students = new string[3] { "James", "Alex", "Fernando" };
for (int i = 0; i < students.Length; i++)
Console.WriteLine(students[i]);
}
}
Trong Đoạn mã trên, lớp SingleDimensionArray lưu trữ tên của sinh viên trong mảng students.
Một biến số nguyên i được khai báo trong vòng lặp For để chỉ ra tổng số sinh viên cần được hiển thị. Sử dụng vòng lặp For, tên của sinh viên được hiển thị là đầu ra.
Kết quả:
James
Alex
Fernando
Mảng Đa Chiều
Hãy xem xét một tình huống trong đó bạn phải lưu trữ số thứ tự (còn gọi là số đăng ký) của 50 sinh viên và điểm của họ trong ba kỳ thi. Sử dụng một mảng một chiều, bạn cần hai mảng riêng biệt để lưu trữ số thứ tự và điểm tương ứng. Tuy nhiên, sử dụng một mảng đa chiều, bạn chỉ cần một mảng để lưu cả số thứ tự và điểm.
Một mảng đa chiều cho phép bạn lưu trữ sự kết hợp các giá trị của một loại duy nhất trong hai hoặc nhiều chiều. Các chiều của mảng được biểu diễn như hàng và cột tương tự như hàng và cột trong bảng tính Microsoft Excel.
Có hai loại mảng đa chiều. Chúng là:
- Mảng Hình Chữ Nhật: Một mảng hình chữ nhật là một mảng đa chiều trong đó tất cả các chiều được chỉ định có các giá trị không đổi. Mảng hình chữ nhật luôn có cùng số cột cho mỗi hàng.
- Mảng Răng Cưa: Một mảng răng cưa là một mảng đa chiều trong đó một trong số các chiều được chỉ định có thể có kích thước biến đổi. Mảng răng cưa có thể có số cột không đồng đều cho mỗi hàng.
Dưới đây là cú pháp để tạo một mảng hình chữ nhật:
type[.] <arrayName>; // khai báo
arrayName = new type[value1, value2]; // khởi tạo
trong đó,
- type: là kiểu dữ liệu và được theo sau bởi dấu ngoặc vuông.
- arrayName: là tên của mảng.
- value1: xác định số hàng.
- value2: xác định số cột.
Đoạn mã bên dưới minh họa việc sử dụng mảng hình chữ nhật.
using System;
class RectangularArray {
static void Main(string[] args) {
int[,] dimension = new int[4, 5];
int numOne = 0;
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 5; j++) {
dimension[i, j] = numOne;
numOne++;
}
}
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 5; j++) {
Console.Write(dimension[i, j] + " ");
}
Console.WriteLine();
}
}
}
Trong Đoạn mã trên, một mảng hình chữ nhật có tên là dimension được tạo ra với bốn hàng và năm cột. Biến số nguyên numOne được khởi tạo bằng không. Mã sử dụng vòng lặp For lồng nhau để lưu trữ từng giá trị tăng lên của numOne trong mảng dimension. Sau đó, các giá trị này được hiển thị theo định dạng ma trận bằng cách sử dụng lại vòng lặp For lồng nhau. Kết quả:
0 1 2 3 4
5 6 7 8 9
10 11 12 13 14
15 16 17 18 19
Lưu ý: Một mảng đa chiều có thể có tối đa tám chiều.
Mảng cố định và Mảng động
Các mảng có thể là mảng cố định hoặc mảng động. Trong một mảng cố định, số lượng phần tử được xác định tại thời điểm khai báo. Ví dụ, một mảng được khai báo để lưu trữ các ngày trong tuần sẽ có chính xác bảy phần tử. Ở đây, số lượng phần tử được biết và do đó có thể được xác định tại thời điểm khai báo. Do đó, một mảng cố định có thể được sử dụng. Ngược lại, trong một mảng động, kích thước của mảng không cố định tại thời điểm khai báo mà có thể tăng động trong quá trình chạy hoặc khi cần thiết. Ví dụ, một mảng được khai báo để lưu địa chỉ email của tất cả người dùng truy cập vào một trang web cụ thể không thể có độ dài được xác định trước. Trong trường hợp đó, độ dài của mảng không thể được chỉ định tại thời điểm khai báo. Ở đây, phải sử dụng một mảng động. Một mảng động có thể thêm các phần tử vào mảng khi cần thiết. Mảng động được tạo ra bằng cách sử dụng các lớp tích hợp sẵn trong Framework .NET.
Đoạn mã bên dưới thể hiện việc sử dụng mảng cố định.
using System;
class DaysOfWeek {
static void Main(string[] args) {
string[] days = new string[7];
days[0] = "Sunday";
days[1] = "Monday";
days[2] = "Tuesday";
days[3] = "Wednesday";
days[4] = "Thursday";
days[5] = "Friday";
days[6] = "Saturday";
for (int i = 0; i < days.Length; i++) {
Console.WriteLine(days[i]);
}
}
}
Trong ví dụ này, một biến mảng cố định days với kiểu dữ liệu là string được khai báo để lưu trữ bảy ngày trong tuần. Các ngày từ Chủ nhật đến Thứ Bảy được lưu trữ trong các vị trí chỉ mục từ 0 đến 6 của mảng và được hiển thị trên console bằng phương thức Console.WriteLine().
Hình bên dưới hiển thị việc sử dụng các mảng cố định.
Tham chiếu Mảng
Một biến mảng có thể được tham chiếu bởi một biến mảng khác (biến tham chiếu). Trong quá trình tham chiếu, biến mảng tham chiếu đến các giá trị của biến mảng được tham chiếu. Đoạn mã bên dưới thể hiện việc sử dụng tham chiếu mảng.
using System;
class StudentReferences {
public static void Main() {
string[] classOne = { "Allan", "Chris", "Monica" };
string[] classTwo = { "Katie", "Niel", "Mark" };
Console.WriteLine("Students of Class I :\tStudents of Class II");
for (int i = 0; i < 3; i++) {
Console.WriteLine(classOne[i] + "\t\t\t" + classTwo[i]);
}
classTwo = classOne;
Console.WriteLine("\nStudents of class II after referencing Class I:");
for (int i = 0; i < 3; i++) {
Console.WriteLine(classTwo[i] + "");
}
Console.WriteLine();
classTwo[2] = "Mike";
Console.WriteLine("Students of class I after changing the third student in Class II:");
for (int i = 0; i < 3; i++) {
Console.WriteLine(classOne[i] + "");
}
}
}
Trong Đoạn mã bên dưới, classOne được gán cho classTwo; Do đó, cả hai mảng đều tham chiếu đến cùng một bộ giá trị. Do đó, khi phần tử thứ ba của classTwo được thay đổi từ “Monica” thành “Mike”, sẽ thấy thay đổi tương tự ở phần tử thứ ba của classOne.
Hình bên dưới hiển thị việc sử dụng tham chiếu mảng.
Đây là một mảng hình chữ nhật, một mảng hai chiều trong đó mỗi hàng có cùng số cột. Cú pháp sau hiển thị các điểm được lưu trữ trong một mảng hình chữ nhật:
type[,] <variableName>;
variableName = new type[value1, value2];
trong đó,
- type: chỉ định kiểu dữ liệu của các phần tử trong mảng.
- [ , ]: chỉ ra rằng mảng là một mảng hai chiều.
- variableName: là kiểu dữ liệu của các phần tử trong mảng.
- new: là toán tử được sử dụng để khởi tạo mảng.
- value1: chỉ ra số hàng trong mảng hai chiều.
- value2: chỉ ra số cột trong mảng hai chiều.
Đoạn mã bên dưới cho phép người dùng xác định số lượng học sinh, tên của họ, số kỳ thi và điểm số đạt được bởi mỗi học sinh trong từng kỳ thi. Tất cả các điểm này được lưu trữ trong một mảng hình chữ nhật.
using System;
class StudentsScore {
void StudentDetails() {
Console.Write("Enter the number of Students: ");
int noOfStds = Convert.ToInt32(Console.ReadLine());
Console.Write("Enter the number of Exams: ");
int exams = Convert.ToInt32(Console.ReadLine());
string[] stdName = new string[noOfStds];
string[,] details = new string[noOfStds, exams];
for (int i = 0; i < noOfStds; i++) {
Console.WriteLine();
Console.Write("Enter the Student Name: ");
stdName[i] = Convert.ToString(Console.ReadLine());
for (int y = 0; y < exams; y++) {
Console.Write("Enter Score in Exam " + (y + 1) + ": ");
details[i, y] = Convert.ToString(Console.ReadLine());
}
}
Console.WriteLine();
Console.WriteLine("Student ExamDetails");
Console.WriteLine("-------------------");
Console.WriteLine();
Console.WriteLine("Student\t\tMarks");
Console.WriteLine("-------\t\t-----");
for (int i = 0; i < stdName.Length; i++) {
Console.WriteLine(stdName[i]);
for (int j = 0; j < exams; j++) {
Console.WriteLine("\t\t" + details[i, j]);
}
Console.WriteLine();
}
}
static void Main() {
StudentsScore objStudentScore = new StudentsScore();
objStudentScore.StudentDetails();
}
}
Trong Đoạn mã bên trên, lớp StudentScore cho phép người dùng nhập số lượng học sinh trong lớp, tên của học sinh, số kỳ thi đã tổ chức và điểm số đạt được bởi mỗi học sinh trong từng kỳ thi. Lớp khai báo một phương thức StudentDetails, chấp nhận thông tin của học sinh và kỳ thi. Biến noOfStds lưu trữ số lượng học sinh mà thông tin của họ sẽ được lưu trữ.
Biến exams lưu trữ số lượng kỳ thi mà học sinh đã tham gia. Mảng stdName lưu trữ tên của học sinh. Kích thước của mảng hình chữ nhật details được xác định bởi các biến noOfStds và exams. Mảng này lưu trữ điểm số đạt được bởi học sinh trong các kỳ thi khác nhau. Một vòng lặp lồng nhau được sử dụng để hiển thị thông tin của học sinh. Trong phương thức Main, một đối tượng được tạo của lớp StudentScore và phương thức StudentDetails được gọi thông qua đối tượng này.
Hình bên dưới hiển thị việc sử dụng một mảng hình chữ nhật.
Mảng răng cưa là một mảng đa chiều và được gọi là một mảng của các mảng. Nó bao gồm nhiều mảng trong đó số phần tử trong mỗi mảng có thể khác nhau. Do đó, các hàng của mảng răng cưa có thể có số cột khác nhau.
Mảng răng cưa tối ưu hóa việc sử dụng bộ nhớ và hiệu suất vì việc truy cập các phần tử trong mảng răng cưa nhanh hơn so với các mảng đa chiều khác.
Ví dụ, hãy xem xét một lớp học có 500 học sinh mà mỗi học sinh đã chọn một số lượng môn học khác nhau. Ở đây, bạn có thể tạo một mảng răng cưa vì số lượng môn học cho mỗi học sinh khác nhau.
Hình bên dưới hiển thị biểu diễn của các mảng răng cưa.
Đoạn mã bên dưới trình bày cách sử dụng các mảng răng cưa để lưu trữ tên các công ty.
using System;
class JaggedArray {
static void Main(string[] args) {
string[][] companies = new string[3][];
companies[0] = new string[] { "Intel", "AMD" };
companies[1] = new string[] { "IBM", "Microsoft", "Sun" };
companies[2] = new string[] { "HP", "Canon", "Lexmark", "Epson" };
for (int i = 0; i < companies.GetLength(0); i++) {
Console.Write("List of companies in group " + (i + 1) + ":\t");
for (int j = 0; j < companies[i].GetLength(0); j++) {
Console.Write(companies[i][j] + " ");
}
Console.WriteLine();
}
}
}
Trong Đoạn mã trên, một mảng răng cưa có tên là companies được tạo với ba hàng. Các giá trị “Intel” và “AMD” được lưu trữ trong hai cột riêng biệt của hàng đầu tiên. Tương tự, các giá trị “IBM”, “Microsoft” và “Sun” được lưu trữ trong ba cột riêng biệt của hàng thứ hai. Cuối cùng, các giá trị “HP”, “Canon”, “Lexmark” và “Epson” được lưu trữ trong bốn cột riêng biệt của hàng thứ ba.
Kết quả:
List of companies in group 1: Intel AMD
List of companies in group 2: IBM Microsoft Sun
List of companies in group 3: HP Canon Lexmark Epson
Sử dụng Vòng lặp foreach cho Mảng
Vòng lặp foreach trong C# là một phần mở rộng của vòng lặp For. Vòng lặp này được sử dụng để thực hiện các hành động cụ thể trên các bộ sưu tập dữ liệu lớn và có thể được sử dụng trên các mảng. Vòng lặp này đọc từng phần tử trong mảng được chỉ định và cho phép bạn thực thi một khối mã cho mỗi phần tử trong mảng. Điều này đặc biệt hữu ích cho các loại tham chiếu, như chuỗi.
Dưới đây là cú pháp cho vòng lặp foreach:
foreach (type<identifier> in <list>) {
// statements
}
trong đó,
- type: kiểu dữ liệu của biến
- identifier: tên biến
- list: tên biến của mảng
Đoạn mã bên dưới hiển thị tên và trạng thái nghỉ phép của mỗi học sinh bằng vòng lặp foreach.
using System;
class Students {
static void Main(string[] args) {
string[] studentNames = new string[3] { "Ashley", "Joe", "Mikel" };
foreach (string studName in studentNames) {
Console.WriteLine("Congratulations!! " + studName + " you have been granted an extra leave");
}
}
}
Trong Đoạn mã trên, lớp Students khởi tạo một biến mảng có tên là studentNames. Biến mảng studentNames lưu trữ tên của các học sinh. Trong vòng lặp foreach, một biến chuỗi studName tham chiếu đến mọi phần tử được lưu trữ trong mảng studentNames. Đối với mỗi phần tử được lưu trữ trong mảng studentNames, vòng lặp foreach hiển thị tên của học sinh và cấp thêm một ngày nghỉ phép cho mỗi học sinh.
Kết quả:
Congratulations Ashley you have been granted an extra leave
Congratulations Joe you have been granted an extra leave
Congratulations Mikel you have been granted an extra leave
Lưu ý: Vòng lặp foreach cho phép bạn duyệt qua một mảng mà không cần phải tải lại mảng trong bộ nhớ. Trong quá trình lặp, các phần tử trong danh sách là chỉ đọc. Để thay đổi giá trị trong mảng, bạn phải sử dụng vòng lặp For bên trong vòng lặp foreach. Vòng lặp Foreach thực thi một lần cho mỗi phần tử của mảng.
Mảng kiểu ngụ ý
Mảng kiểu ngụ ý là một mảng trong đó loại của mảng có thể được xác định bởi các phần tử có mặt trong trình khởi tạo mảng. Sự khác biệt chính giữa một mảng thông thường và mảng kiểu ngụ ý là trong mảng này, bạn không cần phải chỉ định kiểu dữ liệu. Các đặc điểm của mảng kiểu ngụ ý như sau:
Cú pháp:
var array_name = new[] { value1, value2, ..... valueN }
trong đó,
- array_name: là tên của mảng
- value1, value2 ,…. : là các giá trị của mảng
Không cần phải chỉ định kiểu dữ liệu cho tên mảng cũng như các giá trị. Trình biên dịch sẽ suy luận kiểu dữ liệu dựa trên dữ liệu được cung cấp.
Đoạn mã:
using System;
namespace xyz {
class ArrayDemo {
public static void Main() {
var StrikeRate = new[] { 150, 196, 175, 224 };
var flags = new[] { true, false, false };
// Display the contents of the arrays
foreach (int i in StrikeRate)
Console.WriteLine("StrikeRate: {0}", i);
foreach (bool i in flags)
Console.WriteLine("Flags: {0}", i);
}
}
}
Khi mã này được biên dịch, trình biên dịch suy luận StrikeRate là một mảng kiểu int dựa trên dữ liệu số nguyên được cung cấp cho mảng. Tương tự, trình biên dịch suy luận dữ liệu cho flags là kiểu bool dựa trên dữ liệu được cung cấp. Để hiển thị nội dung của cả hai mảng, có thể sử dụng vòng lặp foreach.
Một điểm quan trọng phải tuân theo khi sử dụng mảng kiểu ngụ ý là các phần tử dữ liệu của mảng phải cùng kiểu dữ liệu.
Lớp Array
Giả sử có một đoạn mã lưu trữ điểm của một môn học cho 100 học sinh. Người lập trình muốn sắp xếp các điểm số và để làm điều này, anh ta phải viết mã một cách thủ công để thực hiện việc sắp xếp. Điều này có thể làm phiền và dẫn đến tăng số dòng mã. Tuy nhiên, nếu mảng được khai báo là một đối tượng của lớp Array, các phương thức có sẵn trong lớp Array có thể được sử dụng để sắp xếp mảng.
Lớp Array là một lớp có sẵn trong không gian tên System và là lớp cơ sở cho tất cả các mảng trong C#. Nó cung cấp các phương thức cho các nhiệm vụ khác nhau như tạo, tìm kiếm, sao chép và sắp xếp mảng.
Lớp là một kiểu dữ liệu tham chiếu được sử dụng để khởi tạo biến và xác định các phương thức. Một lớp có thể là một lớp được xác định trong thư viện hệ thống của .NET Framework hoặc có thể là do người dùng tự định nghĩa.
Thuộc tính và phương thức
Lớp Array bao gồm các thuộc tính và phương thức được định nghĩa sẵn trong hệ thống, được sử dụng để tạo và điều chỉnh các mảng trong C#. Những thuộc tính này cũng được gọi là thuộc tính của lớp mảng hệ thống.
- Thuộc tính: Các thuộc tính của lớp Array cho phép bạn chỉnh sửa các phần tử được khai báo trong mảng. Bảng bên dưới mô tả các thuộc tính của lớp Array.
Thuộc tính | Mô tả |
IsFixedSize | Trả về một giá trị boolean, cho biết liệu mảng có có kích thước cố định hay không. Giá trị mặc định là true. |
IsReadOnly | Trả về một giá trị boolean, cho biết liệu một mảng có phải là chỉ đọc (read-only) hay không. Giá trị mặc định là false. |
IsSynchronized | Trả về một giá trị boolean, chỉ ra liệu một mảng có thể hoạt động tốt khi được thực thi bởi nhiều luồng (threads) cùng một lúc hay không. Giá trị mặc định là false. |
Length | Trả về một giá trị số nguyên 32-bit, cho biết tổng số phần tử trong một mảng. |
LongLength | Trả về một giá trị số nguyên 64-bit, biểu thị tổng số phần tử trong một mảng. |
Rank | Trả về một giá trị số nguyên, biểu thị số chiều (rank) của mảng, tức là số lượng kích thước của mảng. |
SyncRoot | Trả về một đối tượng được sử dụng để đồng bộ hóa truy cập vào mảng. |
- Phương thức: Lớp Array cho phép bạn xóa, sao chép, tìm kiếm và sắp xếp các phần tử được khai báo trong mảng. Bảng bên dưới mô tả các phương thức phổ biến nhất trong lớp Array.
Phương thức | Mô tả |
Clear | Xóa tất cả các phần tử trong mảng và đặt kích thước của mảng về 0. |
Copy | Sao chép tất cả các phần tử của mảng một chiều hiện tại sang một mảng một chiều khác, bắt đầu từ vị trí chỉ định. |
GetLength | Trả về số lượng phần tử trong một mảng. |
GetLowerBound | Trả về giới hạn dưới của một mảng. |
GetUpperBound | Trả về giới hạn trên của một mảng. |
Initialize | Khởi tạo mỗi phần tử của mảng bằng cách gọi constructor mặc định của lớp Array. |
Sort | Sắp xếp các phần tử trong mảng một chiều. |
SetValue | Đặt giá trị được chỉ định tại vị trí chỉ định trong mảng. |
GetValue | Lấy giá trị được chỉ định từ vị trí chỉ định trong mảng. |
Sử dụng lớp Array
Lớp Array cho phép bạn tạo các mảng bằng cách sử dụng phương thức CreateInstance(). Phương thức này có thể được sử dụng với các tham số khác nhau để tạo mảng một chiều và đa chiều. Để tạo một mảng bằng lớp này, bạn phải gọi phương thức CreateInstance(), được truy cập bằng cách chỉ định tên lớp vì phương thức được khai báo là tĩnh.
Dưới đây là cú pháp cho chữ ký của phương thức CreateInstance() được sử dụng để tạo một mảng một chiều:
public static Array CreateInstance(Type elementType, int length)
trong đó,
- Array: Trả về tham chiếu đến mảng đã tạo.
- Type: Sử dụng toán tử typeof để ép kiểu tường minh.
- elementType: Là kiểu dữ liệu kết quả khi ép kiểu.
- Length: Xác định độ dài của mảng.
Dưới đây là cú pháp cho chữ ký của phương thức CreateInstance() được sử dụng để tạo một mảng đa chiều:
public static Array CreateInstance(Type elementType, int length1, int length2)
trong đó,
- Length1: Xác định độ dài hàng.
- Length2: Xác định độ dài cột.
Đoạn mã:
using System;
class Subjects {
static void Main(string[] args) {
Array objArray = Array.CreateInstance(typeof(string), 5);
objArray.SetValue("Marketing", 0);
objArray.SetValue("Finance", 1);
objArray.SetValue("Human Resources", 2);
objArray.SetValue("Information Technology", 3);
objArray.SetValue("Business Administration", 4);
for (int i = 0; i <= objArray.GetUpperBound(0); i++) {
Console.WriteLine(objArray.GetValue(i));
}
}
}
Trong đoạn mã trên, lớp Subjects khởi tạo một objArray sử dụng phương thức CreateInstance từ lớp Array. Nó tạo ra một mảng một chiều chứa danh sách các môn học và lưu trữ chúng. Bằng cách sử dụng phương thức GetValue(), tên các môn học được hiển thị trong cửa sổ console.
Lưu ý: Lớp Array có nhiều phương thức CreateInstance(), có thể chấp nhận tham số kiểu số nguyên 64 bit để chứa các mảng có dung lượng lớn.
Để thao tác trên một mảng, lớp Array sử dụng bốn giao diện:
- ICloneable: Giao diện ICloneable thuộc System namespace và chứa phương thức Clone() cho phép bạn tạo ra một bản sao chính xác của đối tượng hiện tại của lớp.
- ICollection: Giao diện ICollection thuộc System.Collections namespace và chứa các thuộc tính để đếm số phần tử, kiểm tra xem các phần tử có đồng bộ hóa hay không và nếu không, có thể đồng bộ hóa chúng trong bộ sưu tập.
- IList: Giao diện IList thuộc System.Collections namespace và cho phép bạn chỉnh sửa các phần tử được xác định trong mảng. Giao diện này định nghĩa ba thuộc tính: IsFixedSize, IsReadOnly và Item
- IEnumerable: Giao diện IEnumerable thuộc System.Collections namespace. Giao diện này trả về một bộ duyệt có thể sử dụng với vòng lặp foreach để duyệt qua một bộ sưu tập các phần tử như một mảng.
Bài tập
- Hiển thị và tính tổng các số lẻ trong C#
- Tìm bội số chung nhỏ nhất (BSCNN) trong C# (sử dụng USCLN)
- Khai báo mảng số 5 phần tử in mảng theo chiều đảo ngược trong C#
- Chia mảng thành mảng chẵn, mảng lẻ trong C#
- Sắp xếp mảng theo thứ tự giảm dần trong C#
Viết chương trinh quản lý sinh viên theo yêu cầu sau:
1.Tạo kiểu dữ liệu theo cấu trúc sau:
name string
country string
birthday string
mark int
- Tạo header menu chương trình
Chuong trinh quan ly SV |
1. Nhap lieu |2. Sap xep SV |3. Phan tich |4. Tim sinh vien |5. Thoat |
Menu sẽ hiển thị khi chương trình bắt đầu
Sau khi người dung chọn tính năng và thực thi xong, trừ option 7 sẽ hiển thị thông báo xem người dung mong muốn tiếp tục không.
Ban muon tiep tuc khong ?
- Co. (bam phim ‘y’, ‘Y’)
- Khong (bam phim ‘n’, ‘N’)
– Clear man hinh ! (bam ‘c’, ‘C’)
Lua chon cua ban:
Nếu người dùng chọn trường hợp không hợp lệ, yêu cầu nhập lại
Lưu ý: chương trình cần đáp ứng được yêu cầu người dùng nhập liệu trước khi sử dụng các option khác, nếu không sẽ thông báo lỗi cho người dùng, buộc người dùng phải input sv trước.
- Nhập vào danh sách sinh viên
Nếu người dùng chọn option 1, chương trình thực hiện những yêu cầu sau:
- Yêu cầu người dùng nhập tổng số SV
- Nhập thông tin của mỗi sinh viên
- Validate thông tin nhập vào theo yêu cầu:
Tuổi (mark) <= 20
Điểm phải => 0 và <= 10
Mô tả tính năng khi input sinh viên:
Nhap vao sinh vien [1]:
Name: Toan
Nationality: VN
Nam sinh: 1992
Diem: 8
Yêu cầu sử dụng pointer cho các hàm làm tính năng làm việc với sinh viên
- Sắp xếp sinh viên theo điểm số giảm dần
Khi người dùng chọn option 2, hiển thị ra danh sách SV sắp xếp theo điểm số giảm dần
Ten |
Que quan |
Nam sinh |
Diem |
Toan |
HN |
1992 |
8 |
Sinh vine 2 |
Vn |
1990 |
7 |
Sinh vien 3 |
QN |
1987 |
5 |
- Tìm kiếm số lượng sinh viên theo quê quán
Khi người dùng chọn option 3: tính toán số lượng sinh viên theo quê quán và hiển thị giống ví dụ sau:
Ket qua phan tich:
+ 2 sinh vien que ‘HN’.
+ 1 sinh vien que ‘Vn’.
- Tìm kiếm sinh viên theo quê quán và điểm
Khi người dùng chọn option 4: Yêu cầu người dùng nhập quê quán và điểm thấp nhất
Hiển thị tất cả những người dùng với quê quán trùng khớp và điểm cao hơn điểm thấp nhất người dùng nhập vào