二維數組在圖像處理、棋盤遊戲、矩陣運算等場景中極為常見。本文實現一個功能完整的動態二維數組框架,支持任意位置插入行/列、元素交換、完整移動軌跡記錄,採用鏈表存儲每個邏輯位置的歷史坐標,展示指鋼操作與內存管理的深度結合。
#define MAX_ROW 9
#define MAX_COL 9
// 坐標節點
typedef struct _Node { int x, y; } Node;
// 軌跡鏈表:記錄某邏輯位置歷經的所有物理坐標
typedef struct _PathNodeList {
Node node;
struct _PathNodeList *pNext;
} PathNodeList;
// 二維數組:每個格子掛一條軌跡鏈表
PathNodeList *g_pGrid[MAX_ROW][MAX_COL];
// 當前有效行列數
typedef struct { int row, col; } CurRowColNum;
static CurRowColNum g_size = {0};
int InitGrid(int rows, int cols) {
if (rows > MAX_ROW || cols > MAX_COL) return -1;
g_size.row = rows; g_size.col = cols;
for (int i = 0; i < rows; ++i)
for (int j = 0; j < cols; ++j) {
Node n = {i, j};
CreatePathNodelist(&g_pGrid[i][j], &n); // 頭節點即初始位置
}
return 0;
}
int SwapNode(Node a, Node b) {
// 取得兩個邏輯位置的當前物理坐標(鏈表尾節點)
Node *pa = GetCurPosition(g_pGrid[a.x][a.y]);
Node *pb = GetCurPosition(g_pGrid[b.x][b.y]);
// 將對方當前位置追加到自己的軌跡鏈表
InsertPathNodeList(g_pGrid[a.x][a.y], pb);
InsertPathNodeList(g_pGrid[b.x][b.y], pa);
// 交換鏈表頭指針,完成邏輯位置映射切換
PathNodeList *tmp = g_pGrid[a.x][a.y];
g_pGrid[a.x][a.y] = g_pGrid[b.x][b.y];
g_pGrid[b.x][b.y] = tmp;
return 0;
}
int InsertRow(int insertRow) {
if (insertRow >= g_size.row) { // 追加到末尾
for (int j = 0; j < g_size.col; ++j) {
Node n = {insertRow, j};
CreatePathNodelist(&g_pGrid[insertRow][j], &n);
}
} else { // 中間插入:先在末尾創建空行,再逐行向上交換
for (int j = 0; j < g_size.col; ++j) {
Node n = {g_size.row, j};
CreatePathNodelist(&g_pGrid[g_size.row][j], &n);
}
for (int i = g_size.row; i > insertRow; --i)
for (int j = 0; j < g_size.col; ++j) {
Node cur = {i-1, j}, nxt = {i, j};
SwapNode(cur, nxt); // 利用交換實現行下沉
}
}
g_size.row++;
return 0;
}
int InsertCol(int insertCol) {
if (insertCol >= g_size.col) { /* 追加列 */ }
else {
for (int i = 0; i < g_size.row; ++i) { /* 末尾創建空列 */ }
for (int j = g_size.col; j > insertCol; --j)
for (int i = 0; i < g_size.row; ++i) {
Node cur = {i, j-1}, nxt = {i, j};
SwapNode(cur, nxt); // 列右移
}
}
g_size.col++;
return 0;
}
int GetNodePath(Node logical, PathNodeList **ppOut) {
if (logical.x < 0 || logical.x >= g_size.row ||
logical.y < 0 || logical.y >= g_size.col) return -1;
*ppOut = g_pGrid[logical.x][logical.y];
return 0;
}
int main() {
InitGrid(5,5);
SwapNode((Node){3,4}, (Node){1,1});
InsertRow(1);
InsertCol(3);
PathNodeList *path;
GetNodePath((Node){4,4}, &path);
// 輸出 (4,4) 邏輯位置的歷史軌跡
for (; path; path = path->pNext)
printf("(%d, %d)\n", path->node.x, path->node.y);
DestoryGrid();
return 0;
}
輸出將展示該邏輯位置從初始 (4,4) 經過行/列插入、交換操作後的完整物理坐標遷移路徑。
本框架展示了如何用 C 語言將「數據結構(鏈表)」與「業務語義(二維網格操作)」深度融合。通過指針交換代替數據搬移、鏈表記錄代替狀態機,實現了高效、可追蹤的動態二維數組操作,為棋類 AI、表格編輯器、矩陣變換等應用提供了堅實基礎。