Kỹ Thuật Con Trỏ và Xử Lý Chuỗi Trong Ngôn Ngữ C

Nhiệm vụ 1.1

#include <stdio.h>
#define MAX_SIZE 5

void readData(int elements[], int size);
void printArray(int elements[], int size);
void findMinMaxValues(int elements[], int size, int *minPtr, int *maxPtr);

int main() {
    int data[MAX_SIZE];
    int minValue, maxValue;
    printf("Nhập %d số nguyên:\n", MAX_SIZE);
    readData(data, MAX_SIZE);
    printf("Dữ liệu đã nhập:\n");
    printArray(data, MAX_SIZE);
    printf("Xử lý dữ liệu...\n");
    findMinMaxValues(data, MAX_SIZE, &minValue, &maxValue);
    printf("Kết quả:\n");
    printf("Giá trị nhỏ nhất = %d, giá trị lớn nhất = %d\n", minValue, maxValue);
    return 0;
}

void readData(int elements[], int size) {
    for (int i = 0; i < size; i++) {
        scanf("%d", &elements[i]);
    }
}

void printArray(int elements[], int size) {
    for (int i = 0; i < size; i++) {
        printf("%d ", elements[i]);
    }
    printf("\n");
}

void findMinMaxValues(int elements[], int size, int *minPtr, int *maxPtr) {
    *minPtr = *maxPtr = elements[0];
    for (int i = 1; i < size; i++) {
        if (elements[i] < *minPtr) *minPtr = elements[i];
        else if (elements[i] > *maxPtr) *maxPtr = elements[i];
    }
}
  1. Chức năng của hàm findMinMaxValues là gì?
  2. Khi thực thi dòng 45, con trỏ minPtrmaxPtr trỏ đến đâu?

Nhiệm vụ 1.2

#include <stdio.h>
#define MAX_SIZE 5

void readData(int numbers[], int count);
void displayNumbers(int numbers[], int count);
int *getMaxAddress(int numbers[], int count);

int main() {
    int values[MAX_SIZE];
    int *maxPtr;
    printf("Nhập %d giá trị:\n", MAX_SIZE);
    readData(values, MAX_SIZE);
    printf("Dữ liệu đã nhập:\n");
    displayNumbers(values, MAX_SIZE);
    printf("Xử lý dữ liệu...\n");
    maxPtr = getMaxAddress(values, MAX_SIZE);
    printf("Kết quả:\n");
    printf("Giá trị lớn nhất = %d\n", *maxPtr);
    return 0;
}

void readData(int numbers[], int count) {
    for (int i = 0; i < count; i++) {
        scanf("%d", &numbers[i]);
    }
}

void displayNumbers(int numbers[], int count) {
    for (int i = 0; i < count; i++) {
        printf("%d ", numbers[i]);
    }
    printf("\n");
}

int *getMaxAddress(int numbers[], int count) {
    int maxIndex = 0;
    for (int i = 1; i < count; i++) {
        if (numbers[i] > numbers[maxIndex]) {
            maxIndex = i;
        }
    }
    return &numbers[maxIndex];
}
  1. Hàm getMaxAddress trả về giá trị gì?
  2. Nếu thay thế hàm getMaxAddress bằng đoạn code sau, có hợp lệ không? Giải thích.
    int *getMaxAddress(int numbers[], int count) {
        int max = numbers[0];
        for (int i = 1; i < count; i++) {
            if (numbers[i] > max) {
                max = numbers[i];
            }
        }
        return &max;
    }

Nhiệm vụ 2.1

#include <stdio.h>
#include <string.h>
#define BUFFER_SIZE 80

int main() {
    char str1[BUFFER_SIZE] = "Học tập mang lại niềm vui";
    char str2[BUFFER_SIZE] = "Học tập khiến tôi buồn ngủ";
    char temp[BUFFER_SIZE];
    printf("Kích thước sizeof vs. strlen:\n");
    printf("sizeof(str1) = %d\n", sizeof(str1));
    printf("strlen(str1) = %d\n", strlen(str1));
    printf("\nTrước khi hoán đổi:\n");
    printf("str1: %s\n", str1);
    printf("str2: %s\n", str2);
    printf("\nĐang hoán đổi...\n");
    strcpy(temp, str1);
    strcpy(str1, str2);
    strcpy(str2, temp);
    printf("\nSau khi hoán đổi:\n");
    printf("str1: %s\n", str1);
    printf("str2: %s\n", str2);
    return 0;
}
  1. Kích thước mảng str1 là bao nhiêu? sizeof(str1) tính toán gì? strlen(str1) đếm gì?
  2. Có thể thay thế dòng 6 thành char str1[] = "Học tập mang lại niềm vui"; không? Giải thích.
  3. Việc thực thi dòng 19-21 có hoán đổi nội dung chuỗi không?

Nhiệm vụ 2.2

#include <stdio.h>
#include <string.h>
#define BUFFER_SIZE 80

int main() {
    char *str1 = "Học tập mang lại niềm vui";
    char *str2 = "Học tập khiến tôi buồn ngủ";
    char *temp;
    printf("Kích thước sizeof vs. strlen:\n");
    printf("sizeof(str1) = %d\n", sizeof(str1));
    printf("strlen(str1) = %d\n", strlen(str1));
    printf("\nTrước khi hoán đổi:\n");
    printf("str1: %s\n", str1);
    printf("str2: %s\n", str2);
    printf("\nĐang hoán đổi...\n");
    temp = str1;
    str1 = str2;
    str2 = temp;
    printf("\nSau khi hoán đổi:\n");
    printf("str1: %s\n", str1);
    printf("str2: %s\n", str2);
    return 0;
}
  1. Biến con trỏ str1 lưu trữ gì? sizeof(str1) tính toán gì? strlen(str1) đếm gì?
  2. Có thể thay thế dòng 6 thành char str1[] = "Học tập mang lại niềm vui"; không? So sánh ngữ nghĩa với nhiệm vụ 2.1.
  3. Việc hoán đổi dòng 19-21 thay đổi gì? Nội dung chuỗi có thay đổi không?

Nhiệm vụ 3

#include <stdio.h>

int main() {
    int matrix[2][4] = {{1, 9, 8, 4}, {2, 0, 4, 9}};
    int row, col;
    int *elementPtr;
    int (*arrayPtr)[4];
    printf("Hiển thị 1: Truy cập trực tiếp qua chỉ số\n");
    for (row = 0; row < 2; row++) {
        for (col = 0; col < 4; col++) {
            printf("%d ", matrix[row][col]);
        }
        printf("\n");
    }
    printf("\nHiển thị 2: Truy cập qua con trỏ đến phần tử\n");
    for (elementPtr = &matrix[0][0]; elementPtr < &matrix[0][0] + 8; elementPtr++) {
        printf("%d ", *elementPtr);
        if ((elementPtr - &matrix[0][0] + 1) % 4 == 0) printf("\n");
    }
    printf("\nHiển thị 3: Truy cập qua con trỏ đến mảng một chiều\n");
    for (arrayPtr = matrix; arrayPtr < matrix + 2; arrayPtr++) {
        for (col = 0; col < 4; col++) {
            printf("%d ", (*arrayPtr)[col]);
        }
        printf("\n");
    }
    return 0;
}
  1. Trong khai báo int (*ptr)[4], ptr biểu diễn ý nghĩa gì?
  2. Trong khai báo int *ptr[4], ptr biểu diễn ý nghĩa gì?

Nhiệm vụ 4

#include <stdio.h>
#define MAX_LENGTH 80

void replaceChar(char *text, char target, char replacement);

int main() {
    char content[MAX_LENGTH] = "Lập trình khó khăn hay không, đó là câu hỏi.";
    printf("Văn bản gốc:\n%s\n", content);
    replaceChar(content, 'i', '*');
    printf("Văn bản sau thay đổi:\n%s\n", content);
    return 0;
}

void replaceChar(char *text, char target, char replacement) {
    while (*text) {
        if (*text == target) *text = replacement;
        text++;
    }
}
  1. Chức năng của hàm replaceChar là gì?
  2. Có thể thay điều kiện *text bằng *text != '\0' không?

Nhiệm vụ 5

#include <stdio.h>
#define MAX_LENGTH 80

char *truncateString(char *input, char delimiter);

int main() {
    char text[MAX_LENGTH];
    char ch;
    while (printf("Nhập chuỗi: "), fgets(text, MAX_LENGTH, stdin) != NULL) {
        printf("Nhập ký tự: ");
        ch = getchar();
        printf("Xử lý cắt chuỗi...\n");
        truncateString(text, ch);
        printf("Chuỗi sau cắt: %s\n\n", text);
        getchar();
    }
    return 0;
}

char *truncateString(char *str, char ch) {
    char *pos = str;
    while (*pos != ch) pos++;
    *pos = '\0';
    return pos;
}
  1. Nếu xóa dòng getchar() trong main, kết quả khi nhập nhiều lần sẽ như thế nào?
  2. Chức năng của dòng getchar() là gì?

Nhiệm vụ 6

#include <stdio.h>
#include <string.h>
#define ID_COUNT 5

int validateID(char *id);

int main() {
    char *ids[ID_COUNT] = {
        "31010120000721656X",
        "3301061996X0203301",
        "53010220051126571",
        "510104199211197977",
        "53010220051126133Y"
    };
    for (int i = 0; i < ID_COUNT; i++) {
        printf("%s\t%s\n", ids[i], validateID(ids[i]) ? "Hợp lệ" : "Không hợp lệ");
    }
    return 0;
}

int validateID(char *id) {
    if (strlen(id) != 18) return 0;
    for (int i = 0; i < 17; i++) {
        if (id[i] < '0' || id[i] > '9') return 0;
    }
    char lastChar = id[17];
    return (lastChar >= '0' && lastChar <= '9') || lastChar == 'X';
}

Nhiệm vụ 7

#include <stdio.h>
#include <string.h>
#define MAX_TEXT 80

struct CharNode {
    char letter;
    int next;
    int prev;
};

void encodeText(char *text, int shift);
void decodeText(char *text, int shift);

int main() {
    struct CharNode lower[26], upper[26];
    char input[MAX_TEXT];
    int shift;
    for (int i = 0; i < 26; i++) {
        lower[i].letter = 'a' + i;
        lower[i].next = (i + 1) % 26;
        lower[i].prev = (i - 1 + 26) % 26;
        upper[i].letter = 'A' + i;
        upper[i].next = (i + 1) % 26;
        upper[i].prev = (i - 1 + 26) % 26;
    }
    printf("Nhập văn bản: ");
    fgets(input, MAX_TEXT, stdin);
    printf("Nhập hệ số dịch: ");
    scanf("%d", &shift);
    printf("Văn bản đã mã hóa: ");
    encodeText(input, shift);
    printf("%s\n", input);
    printf("Văn bản đã giải mã: ");
    decodeText(input, shift);
    printf("%s\n", input);
    return 0;
}

void encodeText(char *text, int shift) {
    for (int i = 0; text[i]; i++) {
        if (text[i] >= 'a' && text[i] <= 'z') {
            int pos = text[i] - 'a';
            for (int j = 0; j < shift; j++) {
                pos = lower[pos].next;
            }
            text[i] = lower[pos].letter;
        } else if (text[i] >= 'A' && text[i] <= 'Z') {
            int pos = text[i] - 'A';
            for (int j = 0; j < shift; j++) {
                pos = upper[pos].next;
            }
            text[i] = upper[pos].letter;
        }
    }
}

void decodeText(char *text, int shift) {
    for (int i = 0; text[i]; i++) {
        if (text[i] >= 'a' && text[i] <= 'z') {
            int pos = text[i] - 'a';
            for (int j = 0; j < shift; j++) {
                pos = lower[pos].prev;
            }
            text[i] = lower[pos].letter;
        } else if (text[i] >= 'A' && text[i] <= 'Z') {
            int pos = text[i] - 'A';
            for (int j = 0; j < shift; j++) {
                pos = upper[pos].prev;
            }
            text[i] = upper[pos].letter;
        }
    }
}

Thẻ: C-Language pointers string-manipulation arrays memory-management

Đăng vào ngày 8 tháng 6 lúc 21:04