2014-10-01 3 views
3

나는 문제가 무엇인지 알지 못해서 두통을주는 아주 작은 코드로 비교적 단순한 프로젝트를 가지고있다. 이 아이디어는 http://tweetping.net/과 유사하지만 실시간 트윗을 표시하지는 않지만 사용자와 서비스를 실시간으로 연결합니다.JavaScript, objects and concurrency

서비스는 nodejs를 UPD 수신기로 사용하고 socket.io를 사용하여 웹 브라우저와 통신합니다. Socket.io는 메시지를 듣고 메시지를 받으면 Google지도에 마커를 그립니다. socket.io에서 오는 동시 메시지 (100/S)가 많이있을 때

<script src="https://maps.googleapis.com/maps/api/js?v=3.exp&sensor=false"></script> 
<script src="/socket.io/socket.io.js"></script> 
<script> 
    var socket = io(); 
    var map = false; 
    var markers = {}; 
    var markerTimeouts = {}; 

    $(window).load(function() { 
     var mapOptions = { 
      zoom: 3, 
      center: new google.maps.LatLng(30, 16), 
      mapTypeId: google.maps.MapTypeId.ROADMAP, 
      panControl: false, 
      streetViewControl: false, 
      zoomControlOptions: { 
       style: google.maps.ZoomControlStyle.LARGE, 
       position: google.maps.ControlPosition.TOP_RIGHT 
      },    
     }; 
     map = new google.maps.Map(document.getElementById('map-canvas'), mapOptions); 
    }); 

    function createMarker(name, lng, lat) { 
     var circle = new google.maps.Marker({ 
       position: new google.maps.LatLng(lat, lng), 
       map: map, 
       icon: "/img/marker_red.png?v=2", 
       title: name 
     }); 

     markers[name] = circle; 

     setTimeout(function() { destroyMarker(name); }, 3000); 
    } 

    function destroyMarker(name) { 
     markers[name].setMap(null); 
     delete markers[name]; 
    } 

    socket.on('message', function(data){ 
     if (!map) { 
      return; 
     } 
     else { 
      createMarker(data.name, data.lon, data.lat); 
     } 
    }); 
    </script> 

문제가 발생합니다

이 페이지의 전체 자바 스크립트입니다. 마커는 createMarker 메서드를 통해 잘 만들지 만, 3 초 후에 (setTimeout을 통해) 객체를 제거하려고하면 markers[name] 객체가 정의되지 않습니다.

나는 fiddle.js 예제를 만들지 만 많은 동시 socket.io 메시지를 다시 만들 수는 없습니다.

아무도 javascript가 object[key] = something; 구문을 통해 개체에 뭔가를 밀 수없는 상황이 있습니까? 다른 아이디어?

업데이트 : 참고 사항 : 마커 개체에이 키가 있는지 항상 확인하십시오. 다음 코드를 추가하면 문제가 해결됩니다.

if (name in markers) { 
    return; 
} 
+3

두 번 같은 이름이 나옵니까? – Neo

+0

이 문제는 해결할 수 없지만'setTimeout (destroyMarker.bind (this, name), 3000); '을 사용해야합니다''setMap'이 비동기 적으로 실행되고 있고 함수가 끝나기 전에 삭제가 실행되는지 궁금합니다. 그냥 생각. – bencripps

+1

좋은 생각 들었어! 나는 같은 이름을 가진 makrer를 두 번씩 가질 것이라고 생각하지 않았지만 실제로'if (마커에있는 이름) {return; } '이 문제를 해결했습니다. – markz

답변

1

3 초 후에 같은 이름이 두 번 이상 표시됩니다.

  1. 마커 [이름]
  2. 마커 [이름]
  3. 마커 [이름] 두번째 메시지로부터
  4. 타이머 (제 1 메시지로부터 타이머 후) 삭제 제 메시지로 덮어 제 메시지에서 설정된 이미 끝났지 만 마커 [name]은 이미 삭제되었습니다.