Saya ingin memetakan choropleth dunia untuk tampilan dengan D3, ala:
Saya memiliki dataset yang ingin saya tampilkan yang memiliki kunci ISO-alpha-3. Begitu...
danger.csv
iso,level
AFG,100
ALB,0
DZA,12
dll.
Mengikuti instruksi pada topojson, saya tahu saya bisa melakukan ...
wget "http://www.naturalearthdata.com/http//www.naturalearthdata.com/download/50m/cultural/ne_50m_admin_0_countries.zip"
unzip ne_50m_admin_0_countries.zip
ogr2ogr -f "GeoJSON" output_features.json ne_50m_admin_0_countries.shp -select iso_a3
topojson -o topo.json output_features.json --id-property iso_a3
untuk menghasilkan jmap worldmap yang diidentifikasikan oleh ISO3.
Pertanyaan saya adalah: pada titik apa dalam alur kerja saya harus menggabungkan data dari hazard.csv ke data geo? Saya sebelumnya pernah bekerja dengan qGIS sebagai GUI, tetapi di mana / haruskah / penggabungan terjadi? Di .shp? Setelah ogr2ogr? Secara dinamis di browser setelah menyusut topojson (seperti di sini http://bl.ocks.org/mbostock/4060606 http://bl.ocks.org/mbostock/3306362 )?
Saya cukup baik dengan python, tetapi cukup baru untuk javascript, dan menemukan diri saya menyalin dan menempelkan contoh Bostock lebih dari benar-benar menjadi pembuat kode generatif di sana.
(Saya juga memiliki tindak lanjut terkait, tetapi lebih banyak terlibat di Stackoverflow yang mungkin harus saya migrasi di sini: /programming/18604877/how-to-do-time-data-in-d3-maps )
Jawaban:
Tanyakan kepada diri Anda dua pertanyaan:
Apakah Anda akan menggunakan kembali geografi pada beberapa dataset?
Jika Anda akan menggunakan geografi yang sama dengan beberapa dataset, maka masuk akal untuk memisahkan geografi dan data, dan bergabung dengan mereka di klien. Banyak contoh saya memiliki file CSV (atau TSV) terpisah karena alasan ini. Dengan cara ini, TopoJSON untuk negara bagian dan negara bagian AS atau juga negara dunia dapat digunakan kembali, alih-alih membuat TopoJSON yang terpisah untuk setiap contoh.
Di sisi lain, jika Anda hanya akan menggunakan geografi ini sekali , maka Anda mungkin harus "memanggang" data ke dalam geografi sebagai properti, jika hanya untuk menyederhanakan kode. Pendekatan ini lebih sederhana karena Anda hanya perlu memuat satu file (jadi tidak ada queue.js ), dan karena data disimpan sebagai properti dari setiap fitur, Anda tidak perlu bergabung dengan data di klien (jadi tidak ada d3. peta ).
Catatan: TSV dan CSV seringkali jauh lebih efisien dalam menyimpan properti daripada GeoJSON dan TopoJSON, hanya karena yang terakhir harus mengulangi nama properti pada setiap objek. Ukuran file bisa menjadi alasan lain untuk menyimpan data Anda dalam file terpisah dan bergabung di klien.
Apakah data Anda sudah terikat pada geografi (misalnya, properti shapefile Anda)?
Dengan asumsi Anda menjawab "tidak" untuk pertanyaan pertama dan ingin memanggang data ke dalam geografi (daripada melakukannya di klien), bagaimana Anda melakukan ini tergantung pada format data.
Jika data Anda sudah menjadi properti dari shapefile Anda, maka gunakan
topojson -p
untuk mengontrol properti mana yang disimpan ke file TopoJSON yang dihasilkan. Anda juga dapat menggunakan ini untuk mengubah nama properti dan memaksa mereka ke angka, juga. Lihat Mari Membuat Peta untuk contoh.Jika data Anda dalam file CSV atau TSV yang terpisah, maka gunakan topojson -e (selain
-p
) untuk menentukan file properti eksternal yang dapat digabungkan dengan fitur geografis Anda. Cribbing contoh dari wiki, jika Anda memiliki file TSV seperti ini:Dengan menggunakan
-e
, Anda dapat memetakan ini ke properti output numerik bernama "pengangguran":Contoh dari pendekatan ini adalah choropleth populasi Kentucky, bl.ocks.org/5144735 .
sumber
Pertanyaan bagus. Salah satu contoh yang Anda berikan tampaknya melakukan trik, meskipun sulit untuk diikuti.
Anda akan perhatikan bahwa contoh ini memiliki dua file data eksternal, us.json dan pengangguran.tsv . Anda dapat menganggap pengangguran.tsv seperti bahaya Anda.csv; us.json adalah fitur geografis yang Anda inginkan untuk mengaitkan parameter dari hazard.csv. Yang terakhir, pengangguran.tsv, memiliki
id
danrate
bidang di manaid
sama denganid
di us.json.Di klien dengan D3 Anda harus menggabungkan data dan fitur Anda , setidaknya dengan contoh ini. Hal ini di klien bahwa tingkat pengangguran, dalam contoh ini, bergabung dengan fitur county, menggunakan d3.map () fungsi. Di sinilah diinisialisasi:
Dan ini adalah tempat
rate
dipetakannya keid
:Saya harus mengakui bahwa saya tidak tahu untuk apa
queue()
, tetapi tidak penting untuk diskusi ini. Yang penting untuk dicatat adalah bahwadalamyangid
lapangan di setiap fitur county digantikan oleh pengangguranrate
.rate
sudah dapat diakses oleh identifier bersamaid
( EDIT: Sebagai @ blord-castillo poin, ini sebenarnya adalah generasi array baru asosiatif, atau hash kunci, di manarate
dipetakan keid
). Di sinilahrate
dipanggil untuk keperluan simbologi (di sini, kelas CSS yang tersedia tersedia untuk setiap kuantil):Di mana
quantize()
fungsi mengembalikan nama kelas CSS yang harus digunakan untuk mendesain fitur tersebut (county) berdasarkan tingkat penganggurannya, yang sekarang didefinisikan di bidang fiturid
.sumber
Pertama, baris pertama csv Anda harus berupa daftar nama kolom yang dipisahkan koma untuk menggunakan metode ini. Jika hal ini tidak mungkin, menambahkan komentar tentang hal ini dan saya akan melihat apakah saya bisa mengetahui bagaimana menggunakan
d3.csv.parseRows
bukand3.csv.parse
.d3.csv.parse
dipanggil oleh fungsi penilai pada.defer(function, url, assessor)
.Saya akan menganggap file Anda sekarang terlihat seperti ini:
Dengan ini, Anda dapat membuat hash pencarian dari ISO3 ke tingkat bahaya.
Panduan kode
Pertama Anda membuat objek d3.map () yang akan berfungsi sebagai hash kunci Anda, dan menyimpannya dalam variabel hazardByISO3.
Gunakan antrian untuk memuat paralel.
Memuat topojson Anda sebagai argumen pertama yang diteruskan ke fungsi menunggu (setelah kesalahan). Perhatikan gaya di mana fungsi ini dirantai
queue()
, tetapi terdaftar pada baris terpisah (tidak ada tanda titik kominasi padaqueue()
).Dua hal terjadi di sini. Pertama, Anda memuat hazard.csv sebagai argumen kedua untuk diteruskan ke fungsi menunggu. Seperti yang akan Anda lihat di bawah, argumen ini sebenarnya tidak digunakan. Sebagai gantinya, argumen penilai disediakan untuk fungsi pemuatan, d3.csv. Penilai ini akan memproses setiap baris csv. Dalam hal ini, kami memanggil fungsi set pada hazardByISO3 sehingga untuk setiap kombinasi
iso
kunci, kami menetapkanlevel
sebagai nilai untuk pergi dengan kunci itu. The+d.level
notasi menggunakan unary+
untuk memaksa nilai d.level ke angka.Setelah kedua sumber data dimuat, mereka dilewatkan sebagai dua argumen terpisah untuk fungsi
ready()
. Argumen pertama ke callback selalu merupakan kesalahan pertama yang terjadi. Jika tidak ada kesalahan terjadi, maka nol akan diteruskan sebagai argumen pertama. Argumen kedua adalah sumber data pertama (hasil dari tugas pertama), dan argumen ketiga adalah sumber data kedua (hasil dari tugas kedua).Ini adalah fungsi panggilan balik
ready()
. Pertama-tama kita mengambilerror
argumen yang seharusnya nol jika dua tugas pemuatan selesai dengan sukses (Anda sebenarnya harus menambahkan bahasa untuk menangkap dan menangani kesalahan). Selanjutnya kita mengambil data topojson sebagai objekcountries
. Data ini harus diproses dalam tubuh fungsi dengan sesuatu seperti.data(topojson.feature(world,world.objects.countries).features)
. Karenaready()
tidak mengambil argumen ketiga, hasil dari tugas kedua, csv kami, dibuang begitu saja. Kami hanya menggunakannya untuk membangun hash kunci dan tidak membutuhkannya setelah itu.sumber