web-dev-qa-db-ja.com

nodejsで未定義の値を返すJavaScript関数

データを取得するためのコードを書いています。まず**getsomedata**関数を呼び出してデータを取得し、内部でgetsomedata関数を呼び出します別の関数を呼び出してgetRandomdataを呼び出してデータを取得し、前の関数に戻しますがundefinedを返します。しかし、getRandomdataでは、console.logにデータが表示される可能性があります。 callbacksを使用する必要がありますか?

router.get('/get-data', function (req, res, next) {
    var result = getsomedata(some_parameter);
    console.log(result);   // receiving undefined
    res.send(result);
});

function getsomedata(some_parameter_recieved) {
    var getsomedata = getRandomdata(random_params);
    console.log(getsomedata);    // receiving undefined
    return getsomedata;
}

function getRandomdata(random_params_recieved) {
    // after some calculation 
    console.log(random_data);           // receiving proper data
    return random_data;
}
11
iam

returnの代わりに、callbacksを使用する必要があります。これは、asynchronous操作では、returnI/O操作の完了を待機しないためです。

Callback-JavaScriptでは、高次関数を関数のパラメーターとして渡すことができます。 JavaSCriptはシングルスレッドであるため、一度に1つの操作のみが発生し、発生する各操作はシングルスレッドのキューに入れられます。このように、渡された関数(パラメーターとして)は、親関数の残りの操作(async)が完了したときに実行でき、スクリプトは結果を待機しながら実行を継続できます。

通常、このcallback関数は、関数の最後の引数として渡されます。

Callbacks:を使用

router.get('/get-data', function(req, res, next) {
  getsomedata(some_parameter, function(result) {
    console.log(result);
    res.send(result);
  });
});

function getsomedata(some_parameter_recieved, callback) {
  getRandomdata(random_params, function(random_data) {
    callback(random_data);
  });
}

function getRandomdata(random_params_recieved, callback) {
  // after some calculation
  callback(random_data);
}

Promise:を使用

router.get('/get-data', function(req, res, next) {
  getsomedata(some_parameter, function(result) {
    console.log(result);
    res.send(result);
  });
});

function getsomedata(some_parameter_received, callback) {
  getRandomdata(random_params).then(function(random_data) {
    callback(random_data);
  }).catch(function(e) {
    //handle error here
  });
}

function getRandomdata(random_params_received, callback) {
  return new Promise(function(resolve, reject) {
    // after some calculation
    if (RandomDataGeneratedSuccessfully) {
      resolve(random_data);
    } else {
      reject(reason);
    }
  });
}
30
Rayon