簡體   English   中英

React-native是否不應該僅渲染類似於React工作方式的更改組件?

[英]Shouldn't React-native render only changed components similar to how React works?

我是React領域的新手,但我對它的結構以及至少如何使用它來制作簡單的Webapp相當熟悉,但這使我抓了好幾個小時

我正在使用React-native制作井字游戲,目前僅在Android上進行實驗。 這些是我代碼中的部分,我認為這可以解釋我的情況

import Tile from "./Tile"

export default class Playground extends React.Component {
    constructor(props) {
        super(props)
        this.state = {
            board: [["?", "?", "?"], ["?", "?", "?"], ["?", "?", "?"]],
            turn: "X"
        }
    }

    move(x, y) {
        if (this.state.board[x][y] == "?") {
            var currentTurn = this.state.turn
            var currentBoard = this.state.board
            currentBoard[x][y] = this.state.turn
            this.setState({board: currentBoard});
            //this.isGameOver(x, y);
        }
    }

    isGameOver(x, y) {
        //Game Over Test
    }

    render() {
        return (
            <View style={styles.container}>
                <View style={styles.row}>
                    <Tile onPress={this.move.bind(this, 0, 0)} icon={this.state.board[0][0]}/>
                    <Tile onPress={this.move.bind(this, 0, 1)} icon={this.state.board[0][1]}/>
                    <Tile onPress={this.move.bind(this, 0, 2)} icon={this.state.board[0][2]}/>
                </View>
                <View style={styles.row}>
                    <Tile onPress={this.move.bind(this, 1, 0)} icon={this.state.board[1][0]}/>
                    <Tile onPress={this.move.bind(this, 1, 1)} icon={this.state.board[1][1]}/>
                    <Tile onPress={this.move.bind(this, 1, 2)} icon={this.state.board[1][2]}/>
                </View>
                <View style={styles.row}>
                    <Tile onPress={this.move.bind(this, 2, 0)} icon={this.state.board[2][0]}/>
                    <Tile onPress={this.move.bind(this, 2, 1)} icon={this.state.board[2][1]}/>
                    <Tile onPress={this.move.bind(this, 2, 2)} icon={this.state.board[2][2]}/>
                </View>
            </View>
        )
    }
}

當然還有磁貼的代碼

export default class Tile extends React.Component {
    constructor(props) {
        super(props)
    }

    rand() {
        return Math.random() * 256;
    }

    randColor() {
        return "rgb(" + this.rand() + " ," + this.rand() + " ," + this.rand() + ")";
    }

    determineIcon() {
        if (this.props.icon == "X") {
            return (<Text>O</Text>)
        } else if (this.props.icon == "O") {
            return (<Text>X</Text>)
        } else {
            return null;
        }
    }

    render() {
        console.log("Things are happening!")
        return (
            <TouchableHighlight onPress={this.props.onPress} underlayColor={this.randColor()}>
                <View style={[styles.square, {backgroundColor: this.randColor()}]}>
                    {this.determineIcon()}
                </View>
            </TouchableHighlight>
        )
    }
}

因此,我最初注意到的是,每次我單擊圖塊並將其成功更改為X時,所有顏色都會重新生成,這使我意識到我的應用程序正在重新渲染所有內容。

因此,我認為這是該隨機函數的錯誤,因此決定將所有正方形都設為橙色,但是我想知道它是仍在重新渲染所有內容還是僅渲染了我按下的圖塊,因此我將控制台日志放入其中以查看有多少個渲染正在發生很多次,令我沮喪的是它發生了9次。

我最終從最后8個圖塊中刪除了onPress和icon屬性,並將它們變成完全靜態的對象,並將板子更改為一個簡單的布爾值,然后將其傳遞給第一個圖塊。 但是不,它仍然呈現了所有9個元素!

有人可以告訴我,React-native不應該只渲染與React相似的組件嗎?

最近,我了解到,當設置新狀態(或更改道具)時,此父組件的層次結構中的所有組件都會觸發render函數。 這對於React是正確的,而不是特定於React-Native 這是因為React的shouldComponentUpdate()默認為true

這並不意味着實際上要重新渲染組件 React足夠聰明,可以確定是否需要更新UI,這是稱為“對帳”的過程的一部分。

也就是說,如果您有許多具有深層次結構的組件,則此行為可能會給JS線程帶來一些壓力。 如果遇到性能問題,您可以重寫shouldComponentUpdate來執行自己的邏輯,或者僅繼承React.PureComponent而不是docs中所說的React.Component

如果您確定某個特定組件在分析后運行緩慢,則可以將其更改為從React.PureComponent繼承,該組件通過淺層支持和狀態比較來實現shouldComponentUpdate()。 如果您確定要手工編寫,可以將this.props與nextProps進行比較,並將this.state與nextState進行比較,然后返回false來告訴React可以跳過更新。

暫無
暫無

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

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