0

I am new to react.

    this.state = { histories: [
                   {
                  "qas":[
                    {"question": "hi1", "answer": "hello1"},
                    {"question": "hi2", "answer": "hello2"}

                  ]
                }
              ] };
render(){
    return ( 
      <div>
          <History 
          histories={this.state.histories} />
      </div>
    );
  }

In separate component page, I would like to use react js to render question and answer by loop or map, however I tried map, it didn't recognize map. I have tried for loop, but it didn't get the child attribute from it.

   const history = ({histories}) => { 
     return(
          <div>
              {histories[0].qas[0].question}
          </div>
          <div}>
            {histories[0].qas[0].answer}
          </div>
      );
}
2
  • Show us the code with map Commented May 16, 2017 at 11:44
  • Use map on state.histories as that's the array. Commented May 16, 2017 at 12:00

2 Answers 2

1

Here is an example with map, hope it will help.

const History = ({histories}) => {
  // Quick, hacky way to set key.
  // More on keys in React https://facebook.github.io/react/docs/lists-and-keys.html#keys
  let key = 1;
  const questionsAndAnswers = histories[0].qas.map(child =>
    <div key={key++}>
      <div>{child.question}</div>
      <div>{child.answer}</div>
    </div>
  );

  return (
    <div>{questionsAndAnswers}</div>
  );
};

class Histories extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      histories: [
        {
          "qas":[
            {"question": "hi1", "answer": "hello1"},
            {"question": "hi2", "answer": "hello2"}
          ]
        }
      ]
    };
  }

  render() {
      return(
        <div>
          <History histories={this.state.histories}/>
        </div>
      )
    }
}

ReactDOM.render(
  <Histories/>,
  document.getElementById("history")
);
<div id="history"></div>
<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>

If you remove the “div” from the <div>{questionsAndAnswers}</div>, then you’ll get the error you encountered “A valid React element (or null)…”. If you want to render multiple elements you need to wrap them in a div. More on this https://facebook.github.io/react/docs/jsx-in-depth.html#jsx-children

Sign up to request clarification or add additional context in comments.

5 Comments

@user2235768, accept the answer if it helped you. This will help other people looking for similar solution
@user2235768 Happy to help!
Thanks again, would you want to have a look of this react question, please? stackoverflow.com/questions/44023350/…
@user2235768 Yes, but it was already answered. The problem is with binding, so either of those answers is right. Unfortunately right now I can’t add comments there.
@user2235768 Great, in arrow function “this” has its original meaning from the enclosing context.
1

It does not recognize this histories, because I bet they are undefined at your start.

const history = ({histories}) => {
  if (!histories || histories.length < 1) return (<div>nothing</div>);
  return histories.map(v => (<div>JSON.stringify(v)</div>))
}

Another problem could be this.state.roundshistories. It is undefined in your example.

1 Comment

<History histories={this.state.histories} />histories is pass by this, error message appears when I use your code:A valid React element (or null) must be returned. You may have returned undefined, an array or some other invalid object.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.