use jismeshcode::prelude::*;
#[test]
fn test_first_mesh_boundaries() {
let sw = Coordinate::new(35.333334, 139.0).unwrap();
let mesh = coord_to_mesh(sw, MeshLevel::First).unwrap();
assert_eq!(mesh.as_string(), "5339");
let ne_inside = Coordinate::new(35.999, 139.999).unwrap();
let mesh = coord_to_mesh(ne_inside, MeshLevel::First).unwrap();
assert_eq!(mesh.as_string(), "5339");
let ne_outside = Coordinate::new(36.001, 140.001).unwrap();
let mesh = coord_to_mesh(ne_outside, MeshLevel::First).unwrap();
assert_ne!(mesh.as_string(), "5339");
}
#[test]
fn test_first_mesh_all_digits() {
let coord = Coordinate::new(35.5, 139.5).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::First).unwrap();
assert_eq!(mesh.as_string(), "5339");
let coord = Coordinate::new(35.0, 138.5).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::First).unwrap();
assert_eq!(mesh.as_string(), "5238");
let coord = Coordinate::new(43.0, 141.5).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::First).unwrap();
assert_eq!(mesh.as_string(), "6441");
let coord = Coordinate::new(26.5, 128.0).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::First).unwrap();
assert_eq!(mesh.as_string(), "3928");
}
#[test]
fn test_second_mesh_conversion() {
let coord = Coordinate::new(35.6812, 139.7671).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::Second).unwrap();
assert_eq!(mesh.as_string(), "533946");
let first = to_level(mesh, MeshLevel::First).unwrap();
assert_eq!(first.as_string(), "5339");
}
#[test]
fn test_second_mesh_all_subdivisions() {
let first_mesh = MeshCode::from_str("5339").unwrap();
let children_list = children(first_mesh);
assert_eq!(children_list.len(), 64);
for t in 0..8 {
for u in 0..8 {
let expected = format!("5339{}{}", t, u);
assert!(
children_list.iter().any(|m| m.as_string() == expected),
"Missing second mesh: {}",
expected
);
}
}
}
#[test]
fn test_second_mesh_boundaries() {
let base_lat = 35.666667; let base_lon = 139.75;
let inside = Coordinate::new(base_lat + 0.01, base_lon + 0.01).unwrap();
let mesh = coord_to_mesh(inside, MeshLevel::Second).unwrap();
assert_eq!(mesh.as_string(), "533946");
}
#[test]
fn test_third_mesh_conversion() {
let coord = Coordinate::new(35.6812, 139.7671).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::Third).unwrap();
assert_eq!(mesh.as_string(), "53394611");
}
#[test]
fn test_third_mesh_all_subdivisions() {
let second_mesh = MeshCode::from_str("533946").unwrap();
let children_list = children(second_mesh);
assert_eq!(children_list.len(), 100);
for v in 0..10 {
for w in 0..10 {
let expected = format!("533946{}{}", v, w);
assert!(
children_list.iter().any(|m| m.as_string() == expected),
"Missing third mesh: {}",
expected
);
}
}
}
#[test]
fn test_third_mesh_size() {
let mesh = MeshCode::from_str("53394611").unwrap();
let bounds = mesh_to_bounds(mesh);
let lat_diff = bounds.max_lat() - bounds.min_lat();
let lon_diff = bounds.max_lon() - bounds.min_lon();
assert!((lat_diff - 30.0 / 3600.0).abs() < 1e-10);
assert!((lon_diff - 45.0 / 3600.0).abs() < 1e-10);
}
#[test]
fn test_fourth_half_mesh_conversion() {
let third = MeshCode::from_str("53394611").unwrap();
let bounds = mesh_to_bounds(third);
let center = bounds.center();
let mesh = coord_to_mesh(center, MeshLevel::FourthHalf).unwrap();
let parent_mesh = parent(mesh).unwrap();
assert_eq!(parent_mesh.as_string(), "53394611");
}
#[test]
fn test_fourth_half_mesh_all_subdivisions() {
let third = MeshCode::from_str("53394611").unwrap();
let children_list = children(third);
assert_eq!(children_list.len(), 4);
for i in 1..=4 {
let expected = format!("53394611{}", i);
assert!(
children_list.iter().any(|m| m.as_string() == expected),
"Missing fourth half mesh: {}",
expected
);
}
}
#[test]
fn test_fourth_half_mesh_quadrants() {
let third_str = "53394611";
let third_bounds = mesh_to_bounds(MeshCode::from_str(third_str).unwrap());
let lat_mid = (third_bounds.min_lat() + third_bounds.max_lat()) / 2.0;
let lon_mid = (third_bounds.min_lon() + third_bounds.max_lon()) / 2.0;
let ne = Coordinate::new_unchecked(lat_mid + 0.001, lon_mid + 0.001);
let mesh = coord_to_mesh(ne, MeshLevel::FourthHalf).unwrap();
assert_eq!(mesh.as_string(), "533946111");
let se = Coordinate::new_unchecked(lat_mid - 0.001, lon_mid + 0.001);
let mesh = coord_to_mesh(se, MeshLevel::FourthHalf).unwrap();
assert_eq!(mesh.as_string(), "533946112");
let nw = Coordinate::new_unchecked(lat_mid + 0.001, lon_mid - 0.001);
let mesh = coord_to_mesh(nw, MeshLevel::FourthHalf).unwrap();
assert_eq!(mesh.as_string(), "533946113");
let sw = Coordinate::new_unchecked(lat_mid - 0.001, lon_mid - 0.001);
let mesh = coord_to_mesh(sw, MeshLevel::FourthHalf).unwrap();
assert_eq!(mesh.as_string(), "533946114");
}
#[test]
fn test_fourth_quarter_mesh_conversion() {
let coord = Coordinate::new(35.6812, 139.7671).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::FourthQuarter).unwrap();
let parent_mesh = parent(mesh).unwrap();
assert_eq!(parent_mesh.level(), MeshLevel::Third);
}
#[test]
fn test_fourth_quarter_mesh_range() {
let third = MeshCode::from_str("53394611").unwrap();
let bounds = mesh_to_bounds(third);
let lat_step = (bounds.max_lat() - bounds.min_lat()) / 4.0;
let lon_step = (bounds.max_lon() - bounds.min_lon()) / 4.0;
for i in 0..4 {
for j in 0..4 {
let lat = bounds.min_lat() + (i as f64 + 0.5) * lat_step;
let lon = bounds.min_lon() + (j as f64 + 0.5) * lon_step;
let coord = Coordinate::new_unchecked(lat, lon);
let mesh = coord_to_mesh(coord, MeshLevel::FourthQuarter).unwrap();
let code_str = mesh.as_string();
let last_two = &code_str[code_str.len() - 2..];
let num: u32 = last_two.parse().unwrap();
assert!(
num >= 1 && num <= 16,
"Invalid fourth quarter code: {}",
num
);
}
}
}
#[test]
fn test_fifth_mesh_conversion() {
let coord = Coordinate::new(35.6812, 139.7671).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::Fifth).unwrap();
let parent_mesh = parent(mesh).unwrap();
assert_eq!(parent_mesh.level(), MeshLevel::Third);
let bounds = mesh_to_bounds(mesh);
let lat_diff = bounds.max_lat() - bounds.min_lat();
let lon_diff = bounds.max_lon() - bounds.min_lon();
assert!((lat_diff - 3.0 / 3600.0).abs() < 1e-10);
assert!((lon_diff - 4.5 / 3600.0).abs() < 1e-10);
}
#[test]
fn test_roundtrip_all_levels() {
let original_coord = Coordinate::new(35.6812, 139.7671).unwrap();
for level in [
MeshLevel::First,
MeshLevel::Second,
MeshLevel::Third,
MeshLevel::FourthHalf,
MeshLevel::FourthQuarter,
MeshLevel::Fifth,
] {
let mesh = coord_to_mesh(original_coord, level).unwrap();
let bounds = mesh_to_bounds(mesh);
assert!(
bounds.contains(original_coord),
"Roundtrip failed for level {:?}",
level
);
}
}
#[test]
fn test_roundtrip_precision() {
let test_coords = vec![
(35.6812, 139.7671), (35.6586, 139.7454), (43.0642, 141.3469), (26.2124, 127.6809), (35.0116, 135.7681), ];
for (lat, lon) in test_coords {
let coord = Coordinate::new(lat, lon).unwrap();
let mesh = coord_to_mesh(coord, MeshLevel::Third).unwrap();
let center = mesh_to_center(mesh);
let lat_diff = (center.lat() - lat).abs();
let lon_diff = (center.lon() - lon).abs();
assert!(
lat_diff < 15.0 / 3600.0,
"Latitude difference too large: {}",
lat_diff
);
assert!(
lon_diff < 22.5 / 3600.0,
"Longitude difference too large: {}",
lon_diff
);
}
}
#[test]
fn test_japan_boundary_coordinates() {
let boundary_coords = vec![
(20.5, 136.0), (45.5, 141.0), (35.0, 122.5), (35.0, 153.5), ];
for (lat, lon) in boundary_coords {
let coord = Coordinate::new(lat, lon).unwrap();
for level in [MeshLevel::First, MeshLevel::Second, MeshLevel::Third] {
let mesh = coord_to_mesh(coord, level).unwrap();
let bounds = mesh_to_bounds(mesh);
assert!(bounds.contains(coord));
}
}
}
#[test]
fn test_mesh_code_boundaries() {
let min_coord = Coordinate::new(20.1, 122.1).unwrap();
let max_coord = Coordinate::new(45.9, 153.9).unwrap();
let min_mesh = coord_to_mesh(min_coord, MeshLevel::First).unwrap();
let max_mesh = coord_to_mesh(max_coord, MeshLevel::First).unwrap();
assert_eq!(min_mesh.as_string().len(), 4);
assert_eq!(max_mesh.as_string().len(), 4);
}
#[test]
fn test_conversion_consistency() {
let mesh = MeshCode::from_str("53394611").unwrap();
let bounds = mesh_to_bounds(mesh);
for i in 0..3 {
for j in 0..3 {
let lat =
bounds.min_lat() + (i as f64 + 0.5) / 3.0 * (bounds.max_lat() - bounds.min_lat());
let lon =
bounds.min_lon() + (j as f64 + 0.5) / 3.0 * (bounds.max_lon() - bounds.min_lon());
let coord = Coordinate::new_unchecked(lat, lon);
let converted = coord_to_mesh(coord, MeshLevel::Third).unwrap();
assert_eq!(
converted.as_string(),
mesh.as_string(),
"Inconsistent conversion at ({}, {})",
lat,
lon
);
}
}
}
#[test]
fn test_adjacent_mesh_boundaries() {
let mesh1 = MeshCode::from_str("53394611").unwrap();
let mesh2 = MeshCode::from_str("53394612").unwrap();
let bounds1 = mesh_to_bounds(mesh1);
let bounds2 = mesh_to_bounds(mesh2);
assert!(
(bounds1.max_lon() - bounds2.min_lon()).abs() < 1e-10,
"Adjacent mesh boundaries don't match"
);
}