【问题标题】:Getting TypeError: Cannot read property 'map' of undefined error获取 TypeError:无法读取未定义错误的属性“地图”
【发布时间】:2023-03-23 21:28:01
【问题描述】:

我正在尝试用 redux 学习 react js。

这是我的 View.js

export default HomeView

//Import React
import React from 'react'

//Import Redux Components
import { connect } from 'react-redux';

//Import Action
import { addAcct, upsertAccts, qryAccts, updateAccts } from '../../Counter/modules/counter';

class HomeView extends React.Component {
  constructor (props)
  {
    super(props);
  }
  componentWillMount()
  {
    this.props.dispatch(qryAccts());
    console.log(this.props);
    this.forceUpdate();
  }
  componentDidMount()
  {
    console.log('----Did----',this.props.accts);
  }
  //Perform Upsert Actions
  upsertAccts(e)
  {
    this.props.dispatch(upsertAccts(this.props.accts))
  }

  //Add new Account to the Array
  addAcct(event)
  {
    this.props.dispatch(addAcct());
    console.log('===this.props===',this.props);
  }


  //onChange function to handle when a name is changed
  handleChange(ev,index)
  {
    this.props.dispatch(updateAccts(ev.target.value,index));
  }

  dateChange(e)
  {
    console.log(e.target.value);
  }

  render() {
    console.log('-----this.props.accts-------',this.props.accts);
    return (
      <div>
        <h1>Accounts</h1>
        <ul>
         { this.props.accts.map((v,i) => <li key={i}><input style={{width:'500px'}} onChange={event => this.handleChange(event,i)} value={v.Name}/></li>) }
        </ul>
      </div>
    );
  }
}

//Connects Redux State to React, Injects reducer as a property
//export default Page1Demo;
export default connect(state => ({ accts: state.accts }))(HomeView);

这里是我的减速器操作

// ------------------------------------
// Constants
// ------------------------------------


export const RECEIVED_ACCTS = 'RECEIVED_ACCTS';
export const UPSERT_ACCTS = 'UPSERT_ACCTS';
export const ADD_ACCT = 'ADD_ACCT';
export const UPDATE_ACCTS = 'UPDATE_ACCTS';


// ------------------------------------
// Actions
// ------------------------------------
export function recAccts(accts) {
  console.log('------16----',accts);
  return{
    type: RECEIVED_ACCTS,
    accts: accts
  }
}

export function qryAccts()
{
  return dispatch => {
    ResponsiveCtrl.getAccts(function(r, e) {
      console.log('------26----',r);
      console.log('------26----',e);
      dispatch(recAccts(r))
    },{escape:false});
  }
}

export function upsertAccts(acctStore) {
  return dispatch => {
    ResponsiveCtrl.upsertAccts(acctStore, function(r, e) {
      dispatch(recAccts(r))
    },{escape:false});
  }
}

export function addAcct() {
  return {
    type: ADD_ACCT
  }
}

export function updateAccts(name,index) {
  return {
    type: UPDATE_ACCTS,
    acctName:name,
    listIndex:index
  }
}

/*  This is a thunk, meaning it is a function that immediately
    returns a function for lazy evaluation. It is incredibly useful for
    creating async actions, especially when combined with redux-thunk!

    NOTE: This is solely for demonstration purposes. In a real application,
    you'd probably want to dispatch an action of COUNTER_DOUBLE and let the
    reducer take care of this logic.  */



// ------------------------------------
// Action Handlers
// ------------------------------------

// ------------------------------------
// Reducer
// ------------------------------------
const initialState = [];

//Reducer function
export function accts(state = initialState, action) {
  console.log('==action===',action);
  console.log('==initialState===',initialState);
  console.log('==state===',state);
  switch (action.type) {
  case RECEIVED_ACCTS:
  //Return the Accouts we receive from Salesforce
    state = action.accts;
    return state;
  case UPDATE_ACCTS:
  //Update our array at the specific index
    var newState = state.slice();
    newState[action.listIndex].Name = action.acctName;
    return newState;
  case ADD_ACCT:
  //Add a new Account to our Array
    var newState = state.slice();
    newState.push({Name:""});
    return newState;
  default:
    return state
  }
}

我能够确定问题,但不确定如何解决问题。

问题是首先生成 dom,然后我得到值,这就是为什么我的地图最初是空的,它给了我错误

TypeError: 无法读取未定义的属性“地图”

知道如何解决这个问题。

【问题讨论】:

  • 在连接函数中,你能打印整个状态并显示状态结构吗?
  • @steppefox 你能告诉我如何在那里添加调试。我正在尝试添加但出​​现语法错误
  • 导出默认连接((state) => { console.log(state); return { accts: state.accts }; })(HomeView);
  • @steppefox 我已经为调试日志添加了截图,请检查它是否即将到来
  • 您的商店不包含行为数据,我认为您的减速器未连接到商店。你如何创建你的商店?你用过 combineReducers 之类的东西吗?

标签: javascript reactjs redux


【解决方案1】:

通过this.props.accts 上的验证将该代码分解为自己的方法。

...

renderAccts () {
  if (Array.isArray(this.props.accts)) {
    return this.props.accts.map((v,i) => <li key={i}><input style={{width:'500px'}} onChange={event => this.handleChange(event,i)} value={v.Name}/></li>)
  }
  return ''
},

render () {
...
<div>
  <h1>Accounts</h1>
  <ul>
    {this.renderAccts()}
  </ul>
</div>
}

这是一个很好的做法,因为您希望确保您从props 获得的正是您所期望的,但如果事实证明您的初始假设不是导致问题。您现在可以在地图前轻松添加console.log(this.props.accts) 并查看发生了什么。每次收到新的道具(触发渲染)时都会调用此方法。如果在第一次调用 render 时该属性未定义,如果您尝试对其进行映射,您将收到此错误。如果问题仍然存在,即使通过此验证,您也应该确保您确实得到了您期望的道具。

【讨论】:

  • 这把我带到另一个错误,现在我得到TypeError: Cannot read property 'bind' of undefined ?
  • 不确定是否无法将值绑定到变量
  • 如果您使用的是 chrome 控制台,错误将显示为红色,您可以在右侧单击指向违规行的链接,或展开堆栈跟踪。这对调试很有帮助:)
  • 我不是我应该如何帮助您调试..这是我拍摄的屏幕截图i.imgur.com/UlEjemJ.png我在右侧看不到任何链接
  • 嘿对不起我的小姐。现在没有错误,但我在方法中添加了renderAccts 中的调试,但得到的列表未定义.. 在underfined 之后,我在qryAccts 中添加了调试此方法 lino no 26 我得到了调试
猜你喜欢
  • 2021-11-09
  • 2021-03-29
  • 1970-01-01
  • 1970-01-01
  • 2022-01-14
  • 1970-01-01
  • 1970-01-01
  • 2019-03-02
相关资源
最近更新 更多