0

I've only started to learn how to refactor code and I'm failing at abstracting a simple function. I pass the parameters into checkAnwser and it works, but count is "lost"

I can't get/append "count" here:

jsfiddle

<input data-correctanswer="javascript" id="answer1" name="" type="text">This works fine (no special chars)
<br/>
<button id="btn1">check 1</button>
<br/>
<input data-correctanswer="jávascripté" id="answer2" name="" type="text"> 
<br/>
<button id="btn2">check 2</button>
<div style="border: 1px solid;" id="result"></div>

Javascript:

 $(document).ready(function () {

         var count;
         $('#btn1').click(function () {
             checkAnswer($('#answer1').data('correctanswer'), $('#answer1').val());
             $('#result').append('result: ').append(count); <-- does not read count
     }); // end of click
     $('#btn2').click(function () {
         checkAnswer($('#answer2').data('correctanswer'), $('#answer2').val());
         $('#result').append('result: ').append(count); // <-- does not read count
     }); // end of click


         function checkAnswer(coorAns, UserAnswer) {
             var count = 0;
             //  var coorAns = $('input[type=text]').data('correctanswer');
             //  var UserAnswer = $('input[type=text]').val();
             var mistakesAllowed = 1;

             if (UserAnswer === coorAns) {
                 count = count + 2;
             }
             for (i = 0; i < coorAns.length; i++) {
                 if (coorAns.charAt(i) !== UserAnswer.charAt(i)) {
                     mistakesAllowed--; // reduce one mistake allowed
                     if (mistakesAllowed < 1) { // and if you have more mistakes than allowed
                         count = count + 1;
                     }
                     if (mistakesAllowed < 0) {
                         count = count - 2
                         break;
                     }
                 }
             }
             console.log('final count: ' + count);
             return count;
         }

     });
Andrejs
  • 10,803
  • 4
  • 43
  • 48
  • 2
    You're returning `count` but you're not storing it anywhere, you're misunderstanding variable scope and how returning values from a function works. – adeneo Aug 09 '15 at 13:24
  • 1
    You'll need `var count = checkAnswer(args);` – adeneo Aug 09 '15 at 13:24
  • I guess that's what I get for learning .slideDown() and .addClass() first, and actual programming after. Thanks :) – Andrejs Aug 09 '15 at 13:46

2 Answers2

3

What Adeneo said:

 var count; //here it's defined.
 $('#btn1').click(function () {
     count = checkAnswer($('#answer1').data('correctanswer'), $('#answer1').val());
     $('#result').append('result: ').append(count); 
 }); // end of click
 $('#btn2').click(function () {
     count = checkAnswer($('#answer2').data('correctanswer'), $('#answer2').val());
     $('#result').append('result: ').append(count); 
 }); // end of click

Your function checkAnswer returns a value called count. That value can be assigned to the variable count.

Probably the chain of thought you had was that assigning count in the function checkAnswer would also assign it to the variable count outside the function. However those two variables are in two different scopes and are not connected to eachother unless you assign the result of the function to the variable count outside the function.

To be more precise:

checkAnswer is in the same scope as the first count variable. That means you could do this:

var count = 0;
console.log(count); //will log 0.
function checkAnswer()
{
   count = 1;
}
checkAnswer();
console.log(count); //will log 1.

However when you use the operator var inside a function it will create a variable that is bound to the scope of the function (it becomes a private variable) only accessible within that function. Unless you return it to a variable outside the scope of that function.

var count = 0;
console.log(count); //will log 0.
function checkAnswer()
{
   var count = 1;
}
checkAnswer();
console.log(count); //will log 0. 

More on scopes on Stack Overflow:

What is the scope of variables in JavaScript?

Bonus:

A little efficiency suggestion for your code

 var count;
 $('#btn1', '#btn2').click(function () {
     var buttonId = $(this).attr("id").substr(4); //will result in 1 or 2
     count = checkAnswer($('#answer' + buttonId ).data('correctanswer'), $('#answer' + buttonId ).val());
     $('#result').append('result: ').append(count); 
 }); // end of click

This will reduce it to one generic function. So when you need to update your code you only need to update one function, not multiple instances of the same code.

Community
  • 1
  • 1
Mouser
  • 13,132
  • 3
  • 28
  • 54
  • 1
    I wasn't hoping for such a detailed answer AND efficiency suggestions :). Thank you! – Andrejs Aug 09 '15 at 13:48
  • 1
    It's a site for solutions and learning. I find it important to explain an answer so you and I both learn more about programming. – Mouser Aug 09 '15 at 13:53
2

Instead of

 checkAnswer($('#answer2').data('correctanswer'), $('#answer2').val());

use

var count=checkAnswer($('#answer2').data('correctanswer'), $('#answer2').val()); //Stored returned value to count variable.

Now you can access returned value.

Here is your updated fiddle.

Laxmikant Dange
  • 7,606
  • 6
  • 40
  • 65