Skip to content

micttyoid/quantized-pathfinding

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

42 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Quantized-pathfinding

q_astar2d.mp4

Motivation

I had a picking plugin, which is getting bloated. So i decided to separate the algorithmic part.

Currently working algorithm(s)

  • quantized_astar

How does this work

This transforms the input before the target algorithm(pathfinding) and roughly recovers the output.

flowchart LR
    subgraph quantized-pathfinding
        direction LR
        quantizer --> algorithm
        algorithm --> dequantizer
    end
    id1[/input/] --> quantized-pathfinding
    quantized-pathfinding --> id2[/output/]
Loading

Why shoud i use this?

Indeed(to just use algorithm), you don't need to use this. You can, for example, implement float-like type to directly work with pathfinding.

QnA

What'd be different from theory?

It's finite. Use the boundry instead of infinity in from-book procedures.

Any unobvious catch?

The input type seems very generous but it may need more traits or method as you need within the explorative body of the algorithm.

Example

use quantized_pathfinding::{
    directed::*,
    traits::*,
    utils::quantizer::Quantizer,
};

const N_LEVELS: [usize; 2] = [8, 8];
const VEC_A: [f32;2] = [0.0, 0.0];
const VEC_B: [f32;2] = [10.0, 10.0];
const START: [f32;2] =  [1.0, 1.0];
const GOAL: [f32;2] = [9.0, 10.0];

fn main() {
    let solution = q_astar2d_mini();
    for (v1, v2) in solution {
        println!("({:.2},{:.2}) -> ({:.2},{:.2})", v1[0], v1[1], v2[0], v2[1]);
    }
}

fn q_astar2d_mini() -> Vec<([f32; 2], [f32; 2])>{
    let quantizer2d = Quantizer::<f32, 2>::with_n(
        VEC_A, VEC_B, N_LEVELS
    );
    let goal_n = quantizer2d.quantize(GOAL);
    let result = quantized_astar(
        &quantizer2d, START,
        |&[x, y]| {
            let mut neighbors = vec![];
            for &[dx, dy] in &[[1, 0], [-1, 0],[0, 1],[0, -1]] {
                let nx = x as i32 + dx;
                let ny = y as i32 + dy;
                if nx >= 0 && ny >= 0 && nx < N_LEVELS[0] as i32 && 
                    ny < N_LEVELS[1] as i32 {
                    neighbors.push(([nx as usize, ny as usize], 1));
                }
            }
            neighbors
        },
        |&[x, y]| { 0 as u32 },
        |&p| p == goal_n,
    );
    let mut drawable_paths: Vec<([f32; 2], [f32; 2])> = vec![];
    match result {
        Some((path, cost)) => {
            println!("Found 2D path with cost {} ({} steps):", cost, path.len());
            let mut pos_old: [f32; 2] = START;
            for (_, pos_new) in path.iter().enumerate() {
                drawable_paths.push((pos_old, *pos_new));
                pos_old = pos_new.clone();                
            } 
        }
        None => println!("No 2D path found"),
    }
    drawable_paths
}

About

Quantization before pathfinding

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages