2012-02-29 41 views
33

Tôi đang sử dụng này để phân tích một tập tin csv và tạo ra một mảng dữ liệu theo quy định tại docs d3:csv để mảng trong d3.js

d3.csv("afile.csv", function(data) { 
    data.forEach(function(d) { 
    d.date = formatDate.parse(d.date); 
    d.price = +d.price; 
}); 

Tuy nhiên, nếu sau khi phương pháp này tôi cố gắng gọi data[0] nó nói nó không xác định. Đây có phải là vì data là tham chiếu và sau khi d3.csv() nằm ngoài phạm vi bị hủy không? Nếu đây là trường hợp làm thế nào tôi có thể khắc phục điều này. Tôi cần phải tham khảo dữ liệu ra khỏi d3.csv()

Trả lời

120

d3.csv là một phương thức không đồng bộ. Điều này có nghĩa là mã bên trong hàm gọi lại được chạy khi dữ liệu được tải, nhưng mã sau và bên ngoài chức năng gọi lại sẽ được chạy ngay sau khi yêu cầu được thực hiện, khi dữ liệu chưa có sẵn. Nói cách khác:

first(); 
d3.csv("path/to/file.csv", function(rows) { 
    third(); 
}); 
second(); 

Nếu bạn muốn sử dụng các dữ liệu được nạp bởi d3.csv, bạn có cần phải đặt mã mà bên trong hàm callback (nơi third là ở trên):

d3.csv("path/to/file.csv", function(rows) { 
    doSomethingWithRows(rows); 
}); 

function doSomethingWithRows(rows) { 
    // do something with rows 
} 

Hoặc, bạn có thể lưu nó như là một biến toàn cầu trên cửa sổ sau đó bạn có thể tham khảo sau:

var rows; 

d3.csv("path/to/file.csv", function(loadedRows) { 
    rows = loadedRows; 
    doSomethingWithRows(); 
}); 

function doSomethingWithRows() { 
    // do something with rows 
} 

Nếu bạn muốn, bạn cũng có thể gán các dữ liệu được nạp một cách rõ ràng để các đối tượng cửa sổ, thay vì hơn khai báo một biến và sau đó quản lý hai tên gọi khác nhau:

d3.csv("path/to/file.csv", function(rows) { 
    window.rows = rows; 
    doSomethingWithRows(); 
}); 

function doSomethingWithRows() { 
    // do something with rows 
} 
+0

là có anyway để đọc từ MongoDB sử dụng d3.js? –

+0

@SGaber Tôi không nghĩ rằng bạn nên chuyển thông tin đăng nhập DB của mình cho người dùng. – TranslucentCloud

-2

Bạn có thể khai báo một biến ngoài chức năng gọi lại và sau đó gán nó với các giá trị từ csv:

var csv_data; 
d3.csv("afile.csv", function(data) { 
    data.forEach(function(d) { 
    d.date = formatDate.parse(d.date); 
    d.price = +d.price; 
    csv_data = data; 
}); 

và sau đó sử dụng csv_data ngoài callback

+0

Nhưng đó chính xác là vấn đề của tôi. Bất cứ khi nào tôi tham khảo csv_data bên ngoài của cuộc gọi lại tất cả tôi nhận được là không xác định. Bên trong gọi lại là tốt. Đó là lý do tại sao tôi giả định rằng csv_data có một tham chiếu của dữ liệu và do đó một khi hàm vượt quá phạm vi tham chiếu bị hủy. Tuy nhiên, tôi đã giải quyết vấn đề bằng cách làm theo một cách tiếp cận hoàn toàn khác. Cảm ơn bạn đã trả lời –

+1

Ok, xin lỗi không giúp đỡ cuối cùng, nhưng hãy xem xét đăng giải pháp của bạn hoặc thay đổi cách tiếp cận nếu hữu ích để tham khảo trong tương lai cho người dùng khác – msonsona

+1

Cách tiếp cận hoàn toàn khác biệt là gì? – Donnied

3

Tôi nghĩ vấn đề của bạn là thời gian bởi vì nó là một cuộc gọi async. Vì vậy, tải dữ liệu như bạn có nhưng gọi hàm trong mã d3 (trong đó Mike có 'doSomethingWithRows()'). Đừng theo mã d3 của bạn với bất kỳ xử lý nào khác (trong đó Mike có 'second()'), di chuyển mã đó vào hàm 'doSomethingWithRows()'. Nó sẽ có sẵn dữ liệu và bạn có thể ...

0

Tôi nghĩ vấn đề đã được giải quyết nhưng tôi đã gặp phải vấn đề tương tự và thảo luận ở trên không hữu ích. Vì vậy, gửi bài như thế nào tôi đã tìm ra một cách ra khỏi vấn đề này: Ở đây, lý do tại sao data[0] là không xác định có lẽ là vì bản thân dữ liệu không được đọc bởi trình duyệt. Lỗi này có thể do đọc trực tiếp tệp dữ liệu (csv), tức là, bằng cách sử dụng lệnh sau d3.csv("myCSVfile.csv",....). Cách tiếp cận này có thể không hoạt động vì các ứng dụng web thường yêu cầu tải tệp từ máy chủ web (không chắc chắn lý do tại sao đây là trường hợp). Vì vậy, một máy chủ web địa phương cần phải được đưa ra. Sử dụng diễn đàn này để tìm hiểu cách làm: How do I setup a local HTTP server using Python. Mã được cập nhật, nếu bạn sử dụng Python 3 để tạo một máy chủ web cục bộ sẽ là: d3.csv("http://localhost:8000/myCSVfile.csv",.....).