2016-10-08 2 views
0

Wenn Sie sich den folgenden Code ansehen, gibt es eine bessere Möglichkeit, die Anzahl von Elementen zu ermitteln, die ein bestimmtes Schlüssel/Wert-Paar in einem Reaktionszustand enthalten?Intelligentere Methode zum Zählen von Werten in Objekten (JS, React)

Diese Methode scheint, als könnte es einen Engpass verursachen, sobald die Liste, die ich durchmache, groß wird.

Hier ist ein vereinfachtes Beispiel für die Frage auf der Hand:

class App extends React.Component { 
 
    constructor() { 
 
    super(); 
 
    
 
    this.state = { 
 
     animals: [ 
 
     {type: 'cat'}, 
 
     {type: 'dog'}, 
 
     {type: 'cat'}, 
 
     ] 
 
    }; 
 
    } 
 

 
    render() { 
 
    return(
 
     <div className="app"> 
 
     <Categories state={this.state} /> 
 
     </div> 
 
    ); 
 
    } 
 
} 
 

 
class Categories extends React.Component { 
 
    constructor() { 
 
    super(); 
 

 
    this.countItems = this.countItems.bind(this); 
 
    } 
 

 
    countItems(type) { 
 
    var count = 0; 
 
    
 
    for(var i = 0; i < this.props.state.animals.length; i++) { 
 
     if(this.props.state.animals[i].type === type) { 
 
     count++; 
 
     } 
 
    } 
 
    
 
    return count; 
 
    } 
 

 
    render() { 
 
    return(
 
     <div className="categories"> 
 
     <div>Total animals: {this.props.state.animals.length}</div> 
 
     <div>Cats: {this.countItems('cat')}</div> 
 
     <div>Dogs: {this.countItems('dog')}</div> 
 
     </div> 
 
    ); 
 
    } 
 
} 
 

 
ReactDOM.render(<App />, document.getElementById('container'));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script> 
 

 
<div id="container"></div>

Antwort

1

Wenn dieses Verfahren ist man oft nennen würde, dann könnte es zu indizieren Ihre Daten (Tiere) nützlich sein durch Geben Sie diesen Befehl ein, und halten Sie ihn bei Änderungen stets auf dem neuesten Stand.

Zum Beispiel:

Im App Konstruktor Sie eine andere Eigenschaft erzeugen würde animalsPerType:

constructor() { 
    super(); 

    this.state = { 
     animals: [ 
     {type: 'cat'}, 
     {type: 'dog'}, 
     {type: 'cat'}, 
     ] 
    }; 
    this.state.animalsPerType = this.state.animals.reduce(function(acc, animal) { 
     return acc.set(animal.type, (acc.get(animal.type) || []).concat(animal)); 
    }, new Map()); 
    } 

Dann wird Ihr countItems Methode wird trivial:

countItems(type) { 
    return this.props.state.animalsPerType.get(type).length; 
    } 
1

Wenn Sie Sie dann nicht die Struktur Ihres Staates ändern, müssen durch eine Art Schleife tun und zählen durch Art.

Ein ausdrucksvoller Ansatz könnte sein, reduzieren zu verwenden:

countItems(type) { 
    return this.props.state.animals.reduce((acc, next) => { 
     return next.type == type ? acc + 1 : acc) 
    }, 0); 
    } 

Wenn jedoch die Leistung ein Problem ist:

  1. Sie die Zählung in Zustand halten konnte und berechnen einmal jedes Mal animals Änderung

  2. Sie können jeden Tiertyp in ein separates Array im Zustand teilen und dann length auf eac verwenden h.

  3. Ändern der Staat so etwas wie dies könnte helfen:

this.state = { animals: { dogs: [], cats: [] } }

Verwandte Themen