### Find Nearby Restaurants with Geokdbush Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md This example demonstrates building a KDBush index and using geokdbush.around to find nearby restaurants, filtering out specific cuisines and calculating distances. Ensure you have 'kdbush' and 'geokdbush' installed. ```javascript import KDBush from 'kdbush'; import * as geokdbush from 'geokdbush'; // Sample restaurant data const restaurants = [ { id: 1, name: 'Taco Bell', lon: -119.7, lat: 34.43, cuisine: 'Mexican' }, { id: 2, name: 'Pizza Hut', lon: -119.71, lat: 34.44, cuisine: 'Italian' }, { id: 3, name: 'Subway', lon: -119.69, lat: 34.42, cuisine: 'Sandwich' }, { id: 4, name: 'McDonald\'s', lon: -119.72, lat: 34.45, cuisine: 'American' }, ]; // Build index const index = new KDBush(restaurants.length); for (const {lon, lat} of restaurants) { index.add(lon, lat); } index.finish(); // User location const userLng = -119.70; const userLat = 34.43; // Find nearby restaurants function findNearbyRestaurants(lon, lat, maxDistance = 10, limit = 5) { const nearbyIds = geokdbush.around( index, lon, lat, limit, maxDistance, (id) => restaurants[id] && restaurants[id].cuisine !== 'Sandwich' // filter out sandwiches ); return nearbyIds.map(id => { const restaurant = restaurants[id]; const dist = geokdbush.distance(lon, lat, restaurant.lon, restaurant.lat); return { ...restaurant, distance: dist.toFixed(2) }; }); } // Use it const nearby = findNearbyRestaurants(userLng, userLat, 10, 5); console.log(nearby); // Output: Array of restaurants sorted by distance ``` -------------------------------- ### Example Outputs of distance() Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Demonstrates typical return values for the distance() method, showing distances between different geographical points in kilometers. ```javascript 145.7 // Santa Barbara to Los Angeles ``` ```javascript 0.0 // Same point ``` ```javascript 20015.087 // Antipodal points ``` -------------------------------- ### Basic Geokdbush Example Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/index.md Demonstrates building a spatial index with KDBush and using geokdbush's `around()` function to find nearest neighbors and `distance()` to calculate great-circle distance. ```javascript import KDBush from 'kdbush'; import * as geokdbush from 'geokdbush'; const cities = [ { lon: -119.7051, lat: 34.4363 }, // Santa Barbara { lon: -118.2437, lat: 34.0522 }, // Los Angeles { lon: -117.1611, lat: 32.7157 }, // San Diego ]; // Build spatial index const index = new KDBush(cities.length); for (const {lon, lat} of cities) { index.add(lon, lat); } index.finish(); // Find 3 nearest cities const nearest = geokdbush.around(index, -119.7051, 34.4363, 3); console.log(nearest); // [0, 1, 2] // Calculate distance const dist = geokdbush.distance(-119.7051, 34.4363, -118.2437, 34.0522); console.log(dist); // ~145.7 km ``` -------------------------------- ### Install Geokdbush and KDBush Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/index.md Install the geokdbush and kdbush packages using npm. KDBush is a required peer dependency. ```bash npm install geokdbush kdbush ``` -------------------------------- ### CommonJS Import Example (Not Recommended) Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Demonstrates how to import the geokdbush library using CommonJS, though ES Modules are recommended for modern JavaScript development. ```javascript // Not recommended; use ESM imports const geokdbush = await import('geokdbush'); ``` -------------------------------- ### ES Modules Import Example - Entire Module Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Shows how to import the entire geokdbush module using ES Modules syntax. This allows access to all exported functions via the module namespace. ```javascript // Entire module import * as geokdbush from 'geokdbush'; geokdbush.around(...); geokdbush.distance(...); ``` -------------------------------- ### Example Output of around() Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Illustrates the format and ordering of point IDs returned by the around() method. The IDs are sorted by distance, with the nearest point first. ```javascript [0, 5, 12, 3] // First point (ID 0) is nearest, last is farthest ``` -------------------------------- ### Package.json Files Array Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Specifies the files to be included when the package is published to npm. This example shows that only 'index.d.ts' is explicitly listed, implying other standard files like 'index.js' and metadata files are included by default or convention. ```json { "files": ["index.d.ts"] } ``` -------------------------------- ### ES Modules Import Example - Specific Functions Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Illustrates importing specific functions like 'around' and 'distance' from the geokdbush library using ES Modules. This approach is often preferred for cleaner code. ```javascript // Specific functions import { around, distance } from 'geokdbush'; around(...); distance(...); ``` -------------------------------- ### TypeScript Configuration for Geokdbush Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Configuration for the TypeScript compiler. This setup is used to generate declaration files from JSDoc annotations in the JavaScript code. ```json { "compilerOptions": { "allowJs": true, "checkJs": true, "strict": true, "emitDeclarationOnly": true, "declaration": true, "target": "es2017" }, "files": ["index.js"] } ``` -------------------------------- ### Create and Populate a KDBush Index Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Initialize a KDBush index with the number of points and add each point's longitude and latitude. Finish building the index after adding all points. ```javascript import KDBush from 'kdbush'; // Your geographic data (points with coordinates) const cities = [ { name: 'Santa Barbara', lon: -119.7051, lat: 34.4363 }, { name: 'Los Angeles', lon: -118.2437, lat: 34.0522 }, { name: 'San Diego', lon: -117.1611, lat: 32.7157 }, ]; // Create index for the number of points const index = new KDBush(cities.length); // Add each point for (const {lon, lat} of cities) { index.add(lon, lat); } // Finish building the index index.finish(); ``` -------------------------------- ### Import TinyQueue for Priority Queue Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Demonstrates the import of the TinyQueue library, used for implementing the priority queue in the branch-and-bound algorithm. ```javascript import TinyQueue from 'tinyqueue' ``` -------------------------------- ### Basic Search with KDBush and Geokdbush Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Demonstrates building a KDBush index with geographical points and performing a basic search for nearby points using geokdbush.around. Requires importing KDBush and geokdbush. ```javascript import KDBush from 'kdbush'; import * as geokdbush from 'geokdbush'; // Data const points = [ { lon: -119.7051, lat: 34.4363 }, // [0] { lon: -118.2437, lat: 34.0522 }, // [1] { lon: -117.1611, lat: 32.7157 }, // [2] ]; // Build index const index = new KDBush(points.length); for (const {lon, lat} of points) index.add(lon, lat); index.finish(); // Query const result = geokdbush.around(index, -119.7051, 34.4363, 2); console.log(result); // [0, 1] ``` -------------------------------- ### Indexing and Querying Points with Geokdbush Source: https://github.com/mourner/geokdbush/blob/main/README.md Demonstrates how to create a KDBush index, add points, and then use geokdbush to find the nearest points to a given location. Ensure points are available and imported. ```javascript import KDBush from 'kdbush'; import * as geokdbush from 'geokdbush'; const index = new KDBush(points.length); for (const {lon, lat} of points) index.add(lon, lat); index.finish(); const nearestIds = geokdbush.around(index, -119.7051, 34.4363, 1000); const nearest = nearestIds.map(id => points[id]); ``` -------------------------------- ### Branch-and-Bound Search Algorithm Steps Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Outlines the steps involved in the branch-and-bound search algorithm for finding nearest neighbors in a kd-tree. ```plaintext 1. Initialize priority queue with root node (entire Earth) 2. While queue not empty: a. Pop closest item from queue b. If it's a point: - Check if within constraints (distance, predicate) - Add to results if valid - Return results if maxResults reached c. If it's a tree node: - Calculate distance bound to node's bounding box - Add child nodes to queue if distance < maxDistance 3. Return results sorted by distance ``` -------------------------------- ### Build KDBush Index Once Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Build the KDBush index once and reuse it for multiple queries to avoid expensive re-computation. Ensure to call `finish()` after adding all points. ```javascript // Good: Build once, reuse for many queries const index = new KDBush(points.length); for (const {lon, lat} of points) index.add(lon, lat); index.finish(); for (const query of queries) { const results = geokdbush.around(index, query.lon, query.lat, 10); } // Bad: Rebuilding the index every time is expensive ``` -------------------------------- ### Troubleshoot Performance Issues Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md For large datasets, query times should be very low (1-5ms for 100k+ points). If queries are slow, check if `maxDistance` is set, if the predicate is efficient, and profile using `console.time`/`console.timeEnd`. ```javascript // For 100k+ points, typical query time is 1-5ms // If queries are slower: // 1. Check if maxDistance is set (enables pruning) const results = geokdbush.around(index, lon, lat, 10, 50); // Better // 2. Check if predicate is expensive // 3. Verify data is not growing unbounded // 4. Profile with: console.time/timeEnd console.time('search'); const results = geokdbush.around(index, lon, lat, 10); console.timeEnd('search'); ``` -------------------------------- ### Troubleshoot Empty Results Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Ensure the KDBush index is properly finished using `index.finish()`. Verify that `maxDistance` is not too small and that the predicate function is not overly restrictive. ```javascript // Problem: No results returned // Check 1: Is the index properly finished? const index = new KDBush(points.length); for (const {lon, lat} of points) index.add(lon, lat); index.finish(); // Must call this // Check 2: Is maxDistance too small? const results = geokdbush.around(index, lon, lat, Infinity, 1000); // 1000 km radius // Check 3: Is the predicate too restrictive? const results = geokdbush.around( index, lon, lat, Infinity, Infinity, (id) => { console.log(`Checking point ${id}`); // Debug which points pass return shouldInclude(id); } ); ``` -------------------------------- ### Geokdbush Project File Structure Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/MANIFEST.md Illustrates the hierarchical organization of documentation files within the Geokdbush project, showing the relationships between different markdown files. ```markdown 00-START-HERE.md ├── index.md ├── getting-started.md ├── REFERENCE.md ├── api-reference/ │ ├── around.md │ └── distance.md ├── architecture.md ├── types.md ├── module-graph.md ├── configuration.md └── errors.md ``` -------------------------------- ### Basic Search for Nearest Points Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/api-reference/around.md Builds a KDBush index from a list of points and finds the IDs of the two nearest neighbors to a specified query location. ```javascript import KDBush from 'kdbush'; import * as geokdbush from 'geokdbush'; const points = [ { id: 1, lon: -119.7051, lat: 34.4363 }, // Santa Barbara { id: 2, lon: -118.2437, lat: 34.0522 }, // Los Angeles { id: 3, lon: -117.1611, lat: 32.7157 }, // San Diego ]; // Build KDBush index const index = new KDBush(points.length); for (const {lon, lat} of points) { index.add(lon, lat); } index.finish(); // Find 2 nearest neighbors to a query point const nearestIds = geokdbush.around(index, -119.7051, 34.4363, 2); console.log(nearestIds); // [0, 1, ...] ``` -------------------------------- ### Import geokdbush Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Import the geokdbush library to use its geospatial functions. ```javascript import * as geokdbush from 'geokdbush'; ``` -------------------------------- ### Geokdbush Module Exports Overview Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Lists the main functions and types exported by the geokdbush library. ```text geokdbush (index.js) ├── around() [exported] └── distance() [exported] Types ├── Node [exported type] └── QueueItem [exported type] ``` -------------------------------- ### Initialize TinyQueue for Priority Queue Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/architecture.md Initializes a TinyQueue instance for managing points sorted by distance. The `compareDist` function is essential for maintaining the priority queue's order. ```javascript const q = new TinyQueue([], compareDist); ``` -------------------------------- ### Handle Unfinished KDBush Index Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/errors.md Using a KDBush index before calling `.finish()` can produce incorrect results due to an incomplete internal structure. Always call `index.finish()` after adding all points. ```javascript const index = new KDBush(10); index.add(0, 0); // Missing: index.finish(); // Produces incorrect results due to incomplete structure const result = geokdbush.around(index, 0, 0); ``` -------------------------------- ### Geokdbush Module Imports for Testing Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Imports required for the test file. It imports the entire module as a namespace. ```javascript import test from 'node:test'; import assert from 'node:assert/strict'; import KDBush from 'kdbush'; import cities from 'all-the-cities'; import * as geokdbush from './index.js'; ``` -------------------------------- ### Predicate Application During Tree Traversal Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Illustrates how a predicate function is applied during tree traversal to filter points before adding them to the queue. This optimizes performance by avoiding unnecessary calculations and enabling early termination. ```javascript if (!predicate || predicate(id)) { // Add to queue only if predicate returns true q.push({id, dist}); } ``` -------------------------------- ### Package.json Exports Configuration Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Defines the main entry point, exports, and TypeScript types for the geokdbush package. This configuration affects module resolution, type information, and tree-shaking. ```json { "main": "index.js", "exports": "./index.js", "types": "index.d.ts" } ``` -------------------------------- ### Use Constraints for Faster Queries Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Limit the number of results and the maximum distance to improve query speed. Using constraints allows the library to prune search space more effectively. ```javascript // Good: Limit results and distance const results = geokdbush.around(index, lon, lat, 10, 20); // Faster // Bad: Exhaustive search for every query const results = geokdbush.around(index, lon, lat); // Slower ``` -------------------------------- ### around(index, lng, lat, maxResults?, maxDistance?, predicate?) Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Returns an array of the closest points from a given location in order of increasing distance. This function performs a nearest neighbor search with optional filtering and distance constraints. ```APIDOC ## around(index, lng, lat, maxResults?, maxDistance?, predicate?) ### Description Returns an array of the closest points from a given location in order of increasing distance. ### Method N/A (Function Signature) ### Parameters #### Function Parameters - **index** (KDBush) - Required - The kdbush index to search within. - **lng** (number) - Required - Query point longitude. - **lat** (number) - Required - Query point latitude. - **maxResults** (number) - Optional - Maximum number of points to return. - **maxDistance** (number) - Optional - Maximum distance in kilometers to search within. - **predicate** ((id: number) => boolean) - Optional - A function to filter the results. ### Return Values - **number[]** - An array of point IDs (indices) sorted by distance. ``` -------------------------------- ### Import KDBush Type Definition Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Shows the import of the KDBush default type from 'kdbush' in TypeScript definitions, used for type checking. ```typescript import('kdbush').default [used in type signature] ``` -------------------------------- ### Building a Distance Matrix Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Calculates the pairwise distances between all points in a dataset and stores them in a matrix. This is useful for applications requiring all inter-point distances. ```javascript function buildDistanceMatrix(points) { const n = points.length; const matrix = Array(n).fill(0).map(() => Array(n).fill(0)); for (let i = 0; i < n; i++) { for (let j = i + 1; j < n; j++) { const dist = geokdbush.distance( points[i].lon, points[i].lat, points[j].lon, points[j].lat ); matrix[i][j] = dist; matrix[j][i] = dist; } } return matrix; } ``` -------------------------------- ### around() Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Finds points within a specified radius or number of results around a given longitude and latitude. ```APIDOC ## around() ### Description Finds points within a specified radius or number of results around a given longitude and latitude. ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Method None (Function Call) ### Endpoint None (Function Call) ### Parameters #### around() Parameters - **index** (KDBush) - Required - KDBush spatial index - **lng** (number) - Required - Query longitude in degrees (-180 to 180) - **lat** (number) - Required - Query latitude in degrees (-90 to 90) - **maxResults** (number) - Optional - Max number of points to return (0 to Infinity) - **maxDistance** (number) - Optional - Max search radius in km (0 to Infinity) - **predicate** (function) - Optional - Filter function (item) => bool ### Returns **Type**: `number[]` **Length**: 0 to maxResults **Order**: Ascending by distance (nearest first) **Contents**: Point IDs (indices into the KDBush index) **Early termination conditions**: 1. `result.length === maxResults` — Reached result limit 2. `candidate.dist > maxHaverSinDist` — Exceeded distance limit 3. Queue exhausted — All candidates processed ### Example output ```javascript [0, 5, 12, 3] // First point (ID 0) is nearest, last is farthest ``` ``` -------------------------------- ### Limited Results, No Distance Cap Configuration Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/configuration.md Retrieve a fixed number of nearest points, regardless of their distance. This is useful when you need a specific count of closest items. ```javascript geokdbush.around(index, lng, lat, 100); ``` -------------------------------- ### Nearby Points Configuration Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/configuration.md Retrieve a specific number of points within a defined radius. This is a common use case for finding nearby locations. ```javascript geokdbush.around(index, lng, lat, 10, 5); ``` -------------------------------- ### around Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/index.md Performs a geographic nearest-neighbor search on a KDBush index. It returns an array of point IDs sorted by distance, with optional limits on the number of results and maximum distance, as well as a filter predicate. ```APIDOC ## around ### Description Performs a geographic nearest-neighbor search on a KDBush index. Returns results sorted by distance, with optional filtering and limits. ### Signature ```typescript (index: KDBush, lng: number, lat: number, maxResults?: number, maxDistance?: number, predicate?: (id: number) => boolean): number[] ``` ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Parameters - **index** (KDBush) - The KDBush index to search within. - **lng** (number) - The longitude of the search center. - **lat** (number) - The latitude of the search center. - **maxResults** (number, optional) - The maximum number of results to return. - **maxDistance** (number, optional) - The maximum distance from the center to include results. - **predicate** ((id: number) => boolean, optional) - A function to filter results by point ID. ### Returns - **number[]** - Array of point IDs sorted by distance (nearest first). ### Key features - Returns results in distance order - Efficient branch-and-bound search - Accounts for Earth curvature - Optional distance and count limits - Optional filter predicate ``` -------------------------------- ### Earth Radius and Radian Conversion Constants Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Defines constants for Earth's radius in kilometers and the conversion factor from degrees to radians for calculations. ```javascript const earthRadius = 6371; // Kilometers const rad = Math.PI / 180; // Degrees to radians ``` -------------------------------- ### Combine Constraints for Geospatial Queries Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Use geokdbush.around to find points that satisfy multiple conditions simultaneously: a maximum number of results, a maximum distance, and a custom predicate function. ```javascript // Find up to 5 points within 50 km that meet criteria const results = geokdbush.around( index, -119.7051, 34.4363, 5, // max 5 results 50, // within 50 km (id) => { const city = cities[id]; return city.country === 'USA' && city.population > 50000; } ); ``` -------------------------------- ### Verify Distances of Nearby Points Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/api-reference/distance.md After finding nearby points using `around()`, this snippet iterates through them to calculate and log the precise distance of each point from the query location. Requires an existing index and points data. ```javascript // After using around() to find nearby points, verify distances const nearby = geokdbush.around(index, queryLon, queryLat, Infinity, 100); for (const id of nearby) { const point = points[id]; const dist = geokdbush.distance(queryLon, queryLat, point.lon, point.lat); console.log(`Point ${id}: ${dist.toFixed(2)} km away`); } ``` -------------------------------- ### Geokdbush around() Function Signature Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md The signature for the around() function, used for finding points within a specified radius or distance. ```text (index, lng, lat, maxResults?, maxDistance?, predicate?) => number[] ``` -------------------------------- ### Search with Distance Limit Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/api-reference/around.md Finds all points within a specified radius (in kilometers) from the query location. Use Infinity for maxResults if only distance is a concern. ```javascript // Find all points within 50 kilometers of the query location const nearby = geokdbush.around(index, -119.7051, 34.4363, Infinity, 50); ``` -------------------------------- ### around() Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Finds points around a given longitude and latitude within a specified maximum distance. It can also filter results based on a predicate function. ```APIDOC ## around() ### Description Finds points around a given longitude and latitude within a specified maximum distance. It can also filter results based on a predicate function. ### Signature `(index, lng, lat, maxResults?, maxDistance?, predicate?) => number[]` ### Parameters - **index**: The k-d tree index to search within. - **lng**: The longitude of the search center. - **lat**: The latitude of the search center. - **maxResults** (number, optional): The maximum number of results to return. - **maxDistance** (number, optional): The maximum distance from the center to search. - **predicate** (function, optional): A function to filter results. It receives a point index and should return true to include it. ### Returns An array of indices of the points found. ``` -------------------------------- ### Incremental Search by Distance Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Find points at increasing distances from a given location. This is useful for progressively discovering nearby points. ```javascript // Find points at increasing distances const nearby = []; for (const distance of [10, 20, 50, 100]) { const results = geokdbush.around( index, lng, lat, Infinity, distance ); nearby.push(...results); } ``` -------------------------------- ### Default `around()` Usage Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/configuration.md Find all points without any distance or filtering limitations. This performs an exhaustive search and is useful for complete ordering but can be expensive for large datasets. ```javascript geokdbush.around(index, lng, lat); ``` -------------------------------- ### distance() Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Calculates the distance between two points specified by their longitudes and latitudes. ```APIDOC ## distance() ### Description Calculates the distance between two points specified by their longitudes and latitudes. ### Parameters #### Path Parameters None #### Query Parameters None #### Request Body None ### Method None (Function Call) ### Endpoint None (Function Call) ### Parameters #### distance() Parameters - **lng1** (number) - Required - First point longitude (-180 to 180) - **lat1** (number) - Required - First point latitude (-90 to 90) - **lng2** (number) - Required - Second point longitude (-180 to 180) - **lat2** (number) - Required - Second point latitude (-90 to 90) ### Returns **Type**: `number` **Range**: 0 to ≈ 20,015 **Units**: Kilometers **Precision**: Floating-point (IEEE 754 double) ### Example outputs ```javascript 145.7 // Santa Barbara to Los Angeles 0.0 // Same point 20015.087 // Antipodal points ``` ``` -------------------------------- ### Defensive Programming with Input Validation Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/errors.md Implement validation checks for all inputs before calling geokdbush functions to prevent unexpected behavior or errors. This includes validating the index, coordinates, and optional parameters. ```javascript import * as geokdbush from 'geokdbush'; function safeAround(index, lng, lat, maxResults, maxDistance, predicate) { // Validate inputs if (!index || typeof index.ids !== 'object') { throw new Error('Invalid KDBush index'); } if (!Number.isFinite(lng) || lng < -180 || lng > 180) { throw new Error('Longitude must be between -180 and 180'); } if (!Number.isFinite(lat) || lat < -90 || lat > 90) { throw new Error('Latitude must be between -90 and 90'); } if (maxResults && maxResults < 0) { throw new Error('maxResults must be non-negative'); } if (maxDistance && maxDistance < 0) { throw new Error('maxDistance must be non-negative'); } if (predicate && typeof predicate !== 'function') { throw new Error('predicate must be a function'); } return geokdbush.around(index, lng, lat, maxResults, maxDistance, predicate); } ``` -------------------------------- ### Filter Efficiently with Predicates Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Use simple and fast predicate functions for filtering results. Avoid complex lookups or computations within the predicate, as this can significantly slow down queries. ```javascript // Good: Simple predicate checks geokdbush.around(index, lon, lat, Infinity, Infinity, (id) => data[id].active === true ); // Avoid: Complex lookups in predicate geokdbush.around(index, lon, lat, Infinity, Infinity, (id) => complexDatabase.lookup(id).check() // Slow ); ``` -------------------------------- ### TypeScript Type-Only Imports Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Demonstrates how to import types from the geokdbush library in a TypeScript project. These imports are erased during compilation and do not affect the runtime. ```typescript // Type-only imports (TypeScript) import type { Node, QueueItem } from 'geokdbush'; ``` -------------------------------- ### Distance-Limited Search Configuration Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/configuration.md Find all points within a specified maximum distance, without limiting the number of results. Useful when the radius is more important than the count. ```javascript geokdbush.around(index, lng, lat, Infinity, 50); ``` -------------------------------- ### geokdbush.around Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/api-reference/around.md Performs a geographic nearest-neighbor search on a KDBush spatial index, returning point IDs in order of increasing distance from a query location. ```APIDOC ## geokdbush.around ### Description Performs a geographic nearest-neighbor search on a KDBush spatial index, returning point IDs in order of increasing distance from a query location. ### Method `around(index, lng, lat, maxResults?, maxDistance?, predicate?): number[]` ### Parameters #### Path Parameters - **index** (KDBush) - Required - A KDBush spatial index containing indexed points - **lng** (number) - Required - Longitude of the query point in degrees (-180 to 180) - **lat** (number) - Required - Latitude of the query point in degrees (-90 to 90) #### Query Parameters - **maxResults** (number) - Optional - Maximum number of point IDs to return. Defaults to Infinity. - **maxDistance** (number) - Optional - Maximum search radius in kilometers. Defaults to Infinity. - **predicate** ((item: number) => boolean) - Optional - Optional filter function that receives point IDs; returns true to include, false to exclude. Defaults to undefined. ### Return Type **number[]** — An array of point IDs from the index, sorted in order of increasing great-circle distance from the query point. Points are ordered nearest to farthest. ### Usage Examples #### Basic search for nearest points ```javascript import KDBush from 'kdbush'; import * as geokdbush from 'geokdbush'; const points = [ { id: 1, lon: -119.7051, lat: 34.4363 }, // Santa Barbara { id: 2, lon: -118.2437, lat: 34.0522 }, // Los Angeles { id: 3, lon: -117.1611, lat: 32.7157 }, // San Diego ]; // Build KDBush index const index = new KDBush(points.length); for (const {lon, lat} of points) { index.add(lon, lat); } index.finish(); // Find 2 nearest neighbors to a query point const nearestIds = geokdbush.around(index, -119.7051, 34.4363, 2); console.log(nearestIds); // [0, 1, ...] ``` #### Search with distance limit ```javascript // Find all points within 50 kilometers of the query location const nearby = geokdbush.around(index, -119.7051, 34.4363, Infinity, 50); ``` #### Search with filter predicate ```javascript // Find up to 10 points, but only return those matching the predicate const populated = geokdbush.around( index, 30.5, 50.5, 10, Infinity, (id) => { // Only include points where population > 200,000 return cities[id].population > 200000; } ); ``` #### Combined constraints ```javascript // Find up to 5 nearest points within 100km, filtering by condition const results = geokdbush.around( index, -119.7051, 34.4363, 5, // max 5 results 100, // within 100km (id) => points[id].active === true ); ``` ``` -------------------------------- ### Handle Null KDBush Index Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/errors.md Accessing properties of a null index will cause a TypeError. Ensure the index is a valid KDBush instance before use. ```javascript const result = geokdbush.around(null, 0, 0); ``` -------------------------------- ### Build a Distance Matrix Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/api-reference/distance.md Calculates the pairwise great-circle distances between all points in a given array. Useful for creating a matrix of distances for multiple locations. ```javascript // Calculate distances between all pairs of points const points = [ { lon: -119.7051, lat: 34.4363 }, { lon: -118.2437, lat: 34.0522 }, { lon: -117.1611, lat: 32.7157 } ]; const matrix = []; for (let i = 0; i < points.length; i++) { matrix[i] = []; for (let j = 0; j < points.length; j++) { const {lon: lon1, lat: lat1} = points[i]; const {lon: lon2, lat: lat2} = points[j]; matrix[i][j] = geokdbush.distance(lon1, lat1, lon2, lat2); } } ``` -------------------------------- ### Find Nearest Cluster Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Identify the nearest cluster of k points and calculate their average center. This can be used for k-means style clustering. ```javascript // Find k-means style nearest cluster const k = 5; const cluster = geokdbush.around(index, lng, lat, k); const center = cluster.reduce((acc, id) => { const p = points[id]; return { lon: acc.lon + p.lon, lat: acc.lat + p.lat }; }, {lon: 0, lat: 0}); center.lon /= k; center.lat /= k; ``` -------------------------------- ### Find Nearby Points Within a Distance Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Use geokdbush.around to find all points within a specified distance (in km) from a query point. Set the maximum number of results to Infinity to include all points within the distance. ```javascript // Find all cities within 100 km of the query point const nearby = geokdbush.around(index, -119.7051, 34.4363, Infinity, 100); for (const id of nearby) { console.log(cities[id].name); } ``` -------------------------------- ### Query Index for Nearest Points Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/getting-started.md Find the IDs of the N nearest points to a query point using the geokdbush.around function. Map the IDs to retrieve the actual data. ```javascript // Find 3 nearest cities to a query point const nearestIds = geokdbush.around(index, -119.7051, 34.4363, 3); // Get the actual city data const results = nearestIds.map(id => cities[id]); console.log(results); // Output: // [ // { name: 'Santa Barbara', lon: -119.7051, lat: 34.4363 }, // { name: 'Los Angeles', lon: -118.2437, lat: 34.0522 }, // { name: 'San Diego', lon: -117.1611, lat: 32.7157 } // ] ``` -------------------------------- ### Geokdbush distance() Function Signature Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md The signature for the distance() function, used for calculating the distance between two points. ```text (lng1, lat1, lng2, lat2) => number ``` -------------------------------- ### Predicate Filtering in Leaf Node Evaluation Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/architecture.md Applies a predicate function to filter points during leaf node evaluation. This optimization avoids unnecessary distance calculations for points that do not meet the criteria. ```javascript if (!predicate || predicate(id)) { // Only add to queue if predicate passes q.push({id, dist}); } ``` -------------------------------- ### Filtering with `predicate` Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/configuration.md Apply a custom filter function to candidate points during the search. The predicate receives the point ID and should return a boolean indicating whether to include the point. ```javascript geokdbush.around(index, lng, lat, 20, Infinity, id => { return data[id].type === 'store' && data[id].isOpen; }); ``` -------------------------------- ### Geographic Nearest-Neighbor Search Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/index.md Performs a nearest-neighbor search on a KDBush index. Use this for finding points close to a given location, with optional limits on results and distance, and an optional filter. ```typescript import KDBush from 'kdbush'; function around(index: KDBush, lng: number, lat: number, maxResults?: number, maxDistance?: number, predicate?: (id: number) => boolean): number[] { // Implementation details... return []; } ``` -------------------------------- ### Comparator for Priority Queue Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md A comparator function used for the priority queue implementation with TinyQueue. It compares distances. ```javascript function compareDist(a, b) { return a.dist - b.dist; } ``` -------------------------------- ### distance() Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/module-graph.md Calculates the great-circle distance between two points on Earth using their longitude and latitude coordinates. ```APIDOC ## distance() ### Description Calculates the great-circle distance between two points on Earth using their longitude and latitude coordinates. ### Signature `(lng1, lat1, lng2, lat2) => number` ### Parameters - **lng1** (number): Longitude of the first point. - **lat1** (number): Latitude of the first point. - **lng2** (number): Longitude of the second point. - **lat2** (number): Latitude of the second point. ### Returns The distance between the two points in kilometers. ``` -------------------------------- ### Final Distance Conversion to Kilometers Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Shows the formula for converting the transformed Haversine value back to distance in kilometers. ```plaintext distance_km = 2 × 6371 × asin(√(haverSinValue)) ``` -------------------------------- ### QueueItem Type Definition Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/types.md Represents an item in the priority queue during nearest-neighbor search, storing a point's ID and its distance from the query point. Used to manage candidate points. ```typescript type QueueItem = { id: number; dist: number; }; ``` -------------------------------- ### Geokdbush around() Function Signature Source: https://github.com/mourner/geokdbush/blob/main/_autodocs/REFERENCE.md Signature for the `around` function, which finds the nearest neighbors to a given point. It accepts optional parameters for limiting the number of results and the search distance, and an optional predicate function for filtering. ```typescript function around( index: KDBush, lng: number, lat: number, maxResults?: number, maxDistance?: number, predicate?: (id: number) => boolean ): number[] ``` ```javascript /** * Returns an array of the closest points from a given location in order of increasing distance. * * @param {import('kdbush').default} index kdbush index * @param {number} lng Query point longitude * @param {number} lat Query point latitude * @param {number} [maxResults] Maximum number of points to return * @param {number} [maxDistance] Maximum distance in kilometers to search within * @param {(item: number) => boolean} [predicate] A function to filter the results */ ```