8

私はこのような機能を持っています:

function get_projects() {
    var project_names=[];
    knex('projects').select('name').then(function (a) { 
        project_names.push(a);
    })
    return project_names;
}

return project_names;この関数は、ステートメントを完了する前に return ステートメントを実行し、この関数をproject_names.push(a)呼び出した後に得られるものは、データベースに結果があっても空の配列です (関数 a() 内でログに記録すると、これを確認できます)。

4

3 に答える 3

14

knex select() は promise を返すため、then() 関数内でフローを続行できます。

knex('projects').select('name').then(function(projectNames){
    //do something here
    console.log(projectNames);
});
于 2015-03-01T16:24:57.617 に答える
10

Nodejs は非同期であるため、この行knex('projects').select('name').then...が実行されるとすぐに、「return project_names;」という行が返されます。実行されます。お気づきのように、値が入力されるまで待機しませんでした!

メソッドの最後にある標準的な「リターン」は、イベント ベースの Nodejs のプログラミング スタイルとしては適切ではありません。それなりの場所はありますが、より一般的なのはコールバック アプローチです。この新しいアプローチに関するいくつかのチュートリアルを読むことを検討してください (私はこれが好きです)

現在のコードを次のように変更できます。

function print_project_names() {
  get_projects( function(names){
    for( var i = 0; i < names.length; i++ )
    {
      console.log(names[i]+'\n');
    } 
  });
}

function get_projects( callback ) {
  var project_names=[];
  knex('projects').select('name').then(function (a) { 
     project_names.push(a);
     callback(project_names);
  })
}

注: これは最適化されたコードではありません

ここで、プロジェクト名を出力したい場合 (本当の目的がわからない場合)、実際の関数定義を「コールバック」として「get_projects」に渡します。イベントが発生すると、結果がプロジェクト名にプッシュされると、コールバックが新しいリストで呼び出されます。

于 2013-12-17T21:30:24.890 に答える