簡體   English   中英

C# 字符串數組元素未更新

[英]C# string array element not updating

我正在學習 Blazor 在 C# 中創建 web 應用程序。 應用程序中的頁面之一是拼字游戲。 我的實施細節如下:

  • 一塊class 存儲其大小(默認為 15)和高級方格(雙字、雙字母等)。 一個拼字游戲class 實現 UI 創建、操作、數據綁定等...
  • 一個新的Board實例初始化所有方形類型(高級和非高級)
  • 拼字游戲class 有一個Init方法,該方法查看其成員的每個方塊的種類,然后將相應的顏色代碼存儲在字符串 2D 數組中(與板大小相同,以便於訪問)。 后面這個數組就是我說的問題
  • UI 使用具有 15 行的 HTML 表顯示板,每行有 15 個單元格,其樣式屬性使用 Blazor 的特殊語法 @ 與上述字符串數組的相應顏色代碼綁定。 每個單元格還實現了一個onclick回調,為簡單起見,我只是將第一個單元格的顏色(第 0 行第 0 行)更改為被單擊的單元格的顏色

問題:

  • (0, 0) 處的 HTML 單元不會改變其顏色。 起初我認為這是由於綁定問題(也許我使用了錯誤的語法)。 因此,我嘗試將此單元格專門綁定到一個單獨的字符串成員,並且效果很好。 結論:不是綁定問題
  • 這次我在更新字符串數組中的元素之前和之后添加了一些控制台打印,以查看更改是否生效,我發現了問題 打印顯示該元素確實已正確更新,但是一旦回調方法完成,更改就會恢復,並且HTML單元格的顏色保持不變。 這通過再次單擊確認(在任何單元格上,因為它調用相同的回調方法),打印顯示更新的顏色代碼與之前打印的after不同,而是與before相同。 具體來說,印刷品是: Click #1: (before) red (after) blue. Click #2: (before) red (after) blue Click #1: (before) red (after) blue. Click #2: (before) red (after) blue點擊#2的之前應該是藍色的

解決方法:

  • 嘗試將字符串數組從 2D 更改為 1D,同樣的問題
  • 嘗試使用List<string> ,它可以工作。 所以我現在堅持使用 List,但我仍然更喜歡數組,因為 2D 索引訪問語法比使用list[15 * row + col]list[row][col] (嵌套列表)更簡潔

問題:為什么? 為什么陣列不能按預期工作? 顯然它在退出方法之前更新但之后又恢復了

編碼:

Board.cs

public class Board
{
    public enum SquareKind
    {
        White,
        DL,
        TL,
        DW,
        TW,
        Start
    }
    public const int SIZE = 15;
    public readonly (int row, int col) StartPos = (7, 7);
    public SquareKind[,] Squares = new SquareKind[SIZE, SIZE];

    public Board()
    {
        // Initialize premium squares (including starting one)
        Squares[0, 0] = SquareKind.TW;
        Squares[1, 5] = SquareKind.TL;
        Squares[5, 1] = SquareKind.TL;
        Squares[5, 5] = SquareKind.TL;
        Squares[1, 1] = SquareKind.DW;
        Squares[2, 2] = SquareKind.DW;
        Squares[3, 3] = SquareKind.DW;
        Squares[4, 4] = SquareKind.DW;
        Squares[0, 3] = SquareKind.DL;
        Squares[3, 0] = SquareKind.DL;
        Squares[2, 6] = SquareKind.DL;
        Squares[6, 2] = SquareKind.DL;
        Squares[6, 6] = SquareKind.DL;
        Squares[0, 14] = SquareKind.TW;
        Squares[1, 9] = SquareKind.TL;
        Squares[5, 13] = SquareKind.TL;
        Squares[5, 9] = SquareKind.TL;
        Squares[1, 13] = SquareKind.DW;
        Squares[2, 12] = SquareKind.DW;
        Squares[3, 11] = SquareKind.DW;
        Squares[4, 10] = SquareKind.DW;
        Squares[0, 11] = SquareKind.DL;
        Squares[3, 14] = SquareKind.DL;
        Squares[2, 8] = SquareKind.DL;
        Squares[6, 12] = SquareKind.DL;
        Squares[6, 8] = SquareKind.DL;
        Squares[14, 14] = SquareKind.TW;
        Squares[13, 9] = SquareKind.TL;
        Squares[9, 13] = SquareKind.TL;
        Squares[9, 9] = SquareKind.TL;
        Squares[13, 13] = SquareKind.DW;
        Squares[12, 12] = SquareKind.DW;
        Squares[11, 11] = SquareKind.DW;
        Squares[10, 10] = SquareKind.DW;
        Squares[14, 11] = SquareKind.DL;
        Squares[11, 14] = SquareKind.DL;
        Squares[12, 8] = SquareKind.DL;
        Squares[8, 12] = SquareKind.DL;
        Squares[8, 8] = SquareKind.DL;
        Squares[14, 0] = SquareKind.TW;
        Squares[13, 5] = SquareKind.TL;
        Squares[9, 1] = SquareKind.TL;
        Squares[9, 5] = SquareKind.TL;
        Squares[13, 1] = SquareKind.DW;
        Squares[12, 2] = SquareKind.DW;
        Squares[11, 3] = SquareKind.DW;
        Squares[10, 4] = SquareKind.DW;
        Squares[14, 3] = SquareKind.DL;
        Squares[11, 0] = SquareKind.DL;
        Squares[12, 6] = SquareKind.DL;
        Squares[8, 2] = SquareKind.DL;
        Squares[8, 6] = SquareKind.DL;
        Squares[7, 0] = SquareKind.TW;
        Squares[0, 7] = SquareKind.TW;
        Squares[14, 7] = SquareKind.TW;
        Squares[7, 14] = SquareKind.TW;
        Squares[3, 7] = SquareKind.DL;
        Squares[7, 3] = SquareKind.DL;
        Squares[7, 11] = SquareKind.DL;
        Squares[11, 7] = SquareKind.DL;
        Squares[StartPos.row, StartPos.col] = SquareKind.Start;
    }
}

拼字游戲.razor

@page "/scrabble"
@Init()

<table class="scrabble-board">
    <tbody>
        @for (int i = 0; i < 15; i++)
        {
        <tr>
            @for (int j = 0; j < 15; j++)
            {
                var (row, col) = (i, j);  // Must store i, j here as row, col for callback with parameter using i and j

                <td class="scrabble-board"
                    style="background-color: @squareColors[row, col]"
                    @onclick="@(() => SquareOnClick(row, col))" />
            }
        </tr>
        }
    </tbody>
</table>

拼字游戲.razor.cs

public partial class Scrabble
{
    string[,] squareColors = new string[Board.SIZE, Board.SIZE];
    readonly Dictionary<Board.SquareKind, string> colors = new Dictionary<Board.SquareKind, string>
    {
        [Board.SquareKind.White] = "#DDE0DE",
        [Board.SquareKind.DL] = "#87D7F6",
        [Board.SquareKind.TL] = "#25A9DC",
        [Board.SquareKind.DW] = "#F68787",
        [Board.SquareKind.TW] = "#DB1B1B",
        [Board.SquareKind.Start] = "#25DC88"
    };
    Board board = new Board();

    string Init()  // Method returns a null string to be able to run directly on the Blazor page without compiling error
    {
        for (int i = 0; i < Board.SIZE; i++)
            for (int j = 0; j < Board.SIZE; j++)
            {
                var kind = board.Squares[i, j];
                squareColors[i, j] =colors[kind];
            }
        return null;
    }

    void SquareOnClick(int row, int col)
    {
        Console.Write("(before) {0} ", squareColors[0, 0]);
        squareColors[0, 0] = squareColors[row, col];
        Console.WriteLine("(after) {0}", squareColors[0, 0]);
    }
}

為了更好看,我還使用了以下 CSS (在wwwroot/index.html中引用)

.scrabble-board table {
    width: 100%;
    padding-top: 100%
}

.scrabble-board td {
    border: 1px solid black;
    border-radius: 5px;
    width: 50px;
    height: 50px;
    background-size: contain;
}

刪除@Init()並通過覆蓋OnInitialized()進行初始化

using Microsoft.AspNetCore.Components;

public partial class Scrabble : ComponentBase
{

...

    protected override void OnInitialized()
    {
        for (int i = 0; i < Board.SIZE; i++)
            for (int j = 0; j < Board.SIZE; j++)
            {
                var kind = board.Squares[i, j];
                squareColors[i, j] = colors[kind];
            }
    }

...

每次重繪渲染片段時,您都會初始化板。 將 0,0 設置為其默認紅色。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM