4

これが私がやろうとしていることであり、惨めに失敗しています:

車に取り付けられたデバイスからの GPS 測定値で満たされた MongoDB があります。測定値にはタイムスタンプが付けられ、緯度/経度が含まれています。

読み取りごとに、位置、タイムスタンプ、およびその他の情報を含む Position クラスを作成したいと考えています。

これを Google マップにプロットするために、Positions オブジェクトの配列で構成される Route クラスを作成したいと考えています。

上部のメイン関数は、サンプル JSON ファイルからルートをロードし (CSRF の問題を回避するため... 別の話)、Position オブジェクトとルート オブジェクトを適切に作成します。ルートをプロットしようとすると、問題が発生します。

var positions = this.getPositions();

入力すると

console.log(positions);

その行のすぐ下に、位置配列がうまく出力されます。サイズが大きいので少し手間がかかりますが、出来上がりです。

ただし、入力した場合

console.log(positions[0]);

ポジションがまだロードされていないため、機能しません。

私は何をしますか?

http://classy.pocoo.orgの classy.js を使用していますが、これは問題ではないことを確認しました。

function main()
{
    var route = Route('20120928_025650_0');
    route.plot();
}
var Route = Class.$extend({
    __init__ : function(imaging_run_id)  {
        this.imaging_run_id = imaging_run_id;
        this.positions = [];
        this.load();
    },

    getPositions : function() {
        return (this.positions);
    },

    load : function() {
        //var url='http://localhost:5001/gps/by_imaging_run_id/' + this.imaging_run_id;
        var test_url = '/static/20120928_025650_0.json';
        var me = this;
        $.getJSON(test_url, function(route) {
            for(var position in route) {
                var obj = route[position];
                var new_position = Position(obj['_id'], obj['lat'], obj['lng'], obj['timestamp'], obj['epoch_timestamp'], obj['is_valid']);
                me.pushPositions(new_position);
            }
            me.orderPositions();
        })
        .error(function(jqXhr, textStatus, error) {
            alert("ERROR: " + textStatus + ", " + error);
        });
    },

    orderPositions : function() {
        var unsorted_array = this.getPositions();
        var sorted = unsorted_array.sort(function(a,b){ //Custom sort function
            return a['timestamp'] - b['timestamp']; //Sort ascending
        });
        this.setPositions(sorted);
    },

    plot : function() {
        var positions = this.getPositions();
        var points = [];
        var bounds = new google.maps.LatLngBounds();
        for(var i=0; i<positions.length; i++)
        {
            var obj = positions[i];
            var point = new google.maps.LatLng(obj['location'][0], obj['location'][1]);
            points.push(point);
            bounds.extend(point);
        }
        // Create the polyline.
        var route = new google.maps.Polyline({
            path: points,
            strokeColor: '#e81971',
            strokeOpacity: 1.0,
            strokeWeight: 4
        });
        map.fitBounds(bounds);
        route.setMap(map);
    }
});

var Position = Class.$extend({
    __init__ : function(id, lat, lng, timestamp, epoch_timestamp, valid)  {
        this.id = id;
        this.location = [lat, lng];
        this.timestamp = new Date(timestamp);
        this.epoch_timestamp = new Date(epoch_timestamp);
        this.valid = valid;
        this.anchor_location;
    },.....
4

1 に答える 1

3

私がそれを正しく理解していれば、次のようなことをしたいと思うでしょう:

var positions = this.getPositions(function(positions) {
    console.log(positions[0]);
});

つまり、「getPositions」は、位置が正常にロードされると呼び出される単一のコールバック パラメータを受け入れるように記述し、位置配列を渡す必要があります。getPositionsポジションがすでにロードされているかどうかを確認し、ロードされている場合はコールバックを直接呼び出します。それ以外の場合は、それらをコールバックのキュー (例: ) に追加し、すべての位置が読み込まれた後に反復します (関数の近くのthis.positionsLoadedCallbacksどこかにあると思います)。loadme.orderPositions()

たとえば、getPositions関数は次のようになります。

getPositions : function(callback) {
    if(this.positions !== null) {
        callback(this.positions);
        return;
    } 

    this.positionsLoadedCallbacks.push(callback);
},

位置がロードされたことを確認した後 (つまり、loadJSON 成功コールバック) に、次のようなものを配置する必要があります。

for(var i=0; i < this.positionsLoadedCallbacks.length; i++) {
    this.positionsLoadedCallbacks[i](this.positions);
}

そして、初期化することを忘れないでくださいthis.positionsLoadedCallbacks:)

console.log トリビア

console.log(positions)が機能し、console.log(positions[0])機能しない理由は簡単です。オブジェクト参照を に渡すと、小さな「展開」矢印をクリックしてオブジェクト/配列の内部console.logを見ようとすると、オブジェクトが検査されます。もちろん、その矢印をクリックするまでに、ポジションは読み込まれています。ただし、特定の配列要素 (例: ) を渡すと、その値を直接調べて、それがまだであることを確認し、その結果をコンソールに記録しようとします。positions[0]undefined

自分で試してみてください:

var i = [];
console.log([i]);
i.push(123);

Chrome 24 の前のスニペット[Array[0]]がコンソールに表示されますが、展開すると、配列が aslength: 1であり、その最初の要素が123

于 2012-10-22T22:47:52.800 に答える