forked from M-Labs/nalgebra
Merge pull request #899 from dimforge/point_macro
Add a point! macro for constructing points
This commit is contained in:
commit
ef3257bcb8
@ -280,3 +280,34 @@ pub fn dvector(stream: TokenStream) -> TokenStream {
|
|||||||
};
|
};
|
||||||
proc_macro::TokenStream::from(output)
|
proc_macro::TokenStream::from(output)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Construct a fixed-size point directly from data.
|
||||||
|
///
|
||||||
|
/// **Note: Requires the `macro` feature to be enabled (enabled by default)**.
|
||||||
|
///
|
||||||
|
/// Similarly to [`vector!`], this macro facilitates easy construction of points.
|
||||||
|
///
|
||||||
|
/// `point!` is intended to be the most readable and performant way of constructing small,
|
||||||
|
/// points, and it is usable in `const fn` contexts.
|
||||||
|
///
|
||||||
|
/// ## Examples
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// use nalgebra::point;
|
||||||
|
///
|
||||||
|
/// // Produces a Point3<_>
|
||||||
|
/// let v = point![1, 2, 3];
|
||||||
|
/// ```
|
||||||
|
#[proc_macro]
|
||||||
|
pub fn point(stream: TokenStream) -> TokenStream {
|
||||||
|
let vector = parse_macro_input!(stream as Vector);
|
||||||
|
let len = vector.len();
|
||||||
|
let array_tokens = vector.to_array_tokens();
|
||||||
|
let output = quote! {
|
||||||
|
nalgebra::Point::<_, #len> {
|
||||||
|
coords: nalgebra::SVector::<_, #len>
|
||||||
|
::from_array_storage(nalgebra::ArrayStorage([#array_tokens]))
|
||||||
|
}
|
||||||
|
};
|
||||||
|
proc_macro::TokenStream::from(output)
|
||||||
|
}
|
||||||
|
@ -1,9 +1,10 @@
|
|||||||
use nalgebra::{
|
use nalgebra::{
|
||||||
DMatrix, DVector, Matrix1x2, Matrix1x3, Matrix1x4, Matrix2, Matrix2x1, Matrix2x3, Matrix2x4,
|
DMatrix, DVector, Matrix1x2, Matrix1x3, Matrix1x4, Matrix2, Matrix2x1, Matrix2x3, Matrix2x4,
|
||||||
Matrix3, Matrix3x1, Matrix3x2, Matrix3x4, Matrix4, Matrix4x1, Matrix4x2, Matrix4x3, SMatrix,
|
Matrix3, Matrix3x1, Matrix3x2, Matrix3x4, Matrix4, Matrix4x1, Matrix4x2, Matrix4x3, Point,
|
||||||
SVector, Vector1, Vector2, Vector3, Vector4, Vector5, Vector6,
|
Point1, Point2, Point3, Point4, Point5, Point6, SMatrix, SVector, Vector1, Vector2, Vector3,
|
||||||
|
Vector4, Vector5, Vector6,
|
||||||
};
|
};
|
||||||
use nalgebra_macros::{dmatrix, dvector, matrix, vector};
|
use nalgebra_macros::{dmatrix, dvector, matrix, point, vector};
|
||||||
|
|
||||||
fn check_statically_same_type<T>(_: &T, _: &T) {}
|
fn check_statically_same_type<T>(_: &T, _: &T) {}
|
||||||
|
|
||||||
@ -106,6 +107,19 @@ fn vector_small_dims_exhaustive() {
|
|||||||
assert_eq_and_type!(vector![1, 2, 3, 4, 5, 6], Vector6::new(1, 2, 3, 4, 5, 6));
|
assert_eq_and_type!(vector![1, 2, 3, 4, 5, 6], Vector6::new(1, 2, 3, 4, 5, 6));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Skip rustfmt because it just makes the test bloated without making it more readable
|
||||||
|
#[rustfmt::skip]
|
||||||
|
#[test]
|
||||||
|
fn point_small_dims_exhaustive() {
|
||||||
|
assert_eq_and_type!(point![], Point::<i32, 0>::origin());
|
||||||
|
assert_eq_and_type!(point![1], Point1::<i32>::new(1));
|
||||||
|
assert_eq_and_type!(point![1, 2], Point2::new(1, 2));
|
||||||
|
assert_eq_and_type!(point![1, 2, 3], Point3::new(1, 2, 3));
|
||||||
|
assert_eq_and_type!(point![1, 2, 3, 4], Point4::new(1, 2, 3, 4));
|
||||||
|
assert_eq_and_type!(point![1, 2, 3, 4, 5], Point5::new(1, 2, 3, 4, 5));
|
||||||
|
assert_eq_and_type!(point![1, 2, 3, 4, 5, 6], Point6::new(1, 2, 3, 4, 5, 6));
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn vector_const_fn() {
|
fn vector_const_fn() {
|
||||||
// Ensure that vector! can be used in const contexts
|
// Ensure that vector! can be used in const contexts
|
||||||
@ -115,6 +129,15 @@ fn vector_const_fn() {
|
|||||||
const _: Vector6<i32> = vector![1, 2, 3, 4, 5, 6];
|
const _: Vector6<i32> = vector![1, 2, 3, 4, 5, 6];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn point_const_fn() {
|
||||||
|
// Ensure that vector! can be used in const contexts
|
||||||
|
const _: Point<i32, 0> = point![];
|
||||||
|
const _: Point1<i32> = point![1];
|
||||||
|
const _: Point2<i32> = point![1, 2];
|
||||||
|
const _: Point6<i32> = point![1, 2, 3, 4, 5, 6];
|
||||||
|
}
|
||||||
|
|
||||||
// Skip rustfmt because it just makes the test bloated without making it more readable
|
// Skip rustfmt because it just makes the test bloated without making it more readable
|
||||||
#[rustfmt::skip]
|
#[rustfmt::skip]
|
||||||
#[test]
|
#[test]
|
||||||
@ -195,6 +218,23 @@ fn dmatrix_builtin_types() {
|
|||||||
let _: DMatrix<f64> = dmatrix![0.0, 1.0; 2.0, 3.0];
|
let _: DMatrix<f64> = dmatrix![0.0, 1.0; 2.0, 3.0];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn point_builtin_types() {
|
||||||
|
// Check that point! compiles for all built-in types
|
||||||
|
const _: Point<i8, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<i16, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<i32, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<i64, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<isize, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<u8, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<u16, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<u32, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<u64, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<usize, 4> = point![0, 1, 2, 3];
|
||||||
|
const _: Point<f32, 4> = point![0.0, 1.0, 2.0, 3.0];
|
||||||
|
const _: Point<f64, 4> = point![0.0, 1.0, 2.0, 3.0];
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn dvector_builtin_types() {
|
fn dvector_builtin_types() {
|
||||||
// Check that dvector! compiles for all built-in types
|
// Check that dvector! compiles for all built-in types
|
||||||
@ -248,6 +288,15 @@ fn vector_arbitrary_expressions() {
|
|||||||
assert_eq_and_type!(a, a_expected);
|
assert_eq_and_type!(a, a_expected);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[rustfmt::skip]
|
||||||
|
#[test]
|
||||||
|
fn point_arbitrary_expressions() {
|
||||||
|
// Test that point! supports arbitrary expressions for its elements
|
||||||
|
let a = point![1 + 2, 2 * 3, 4 * f(5 + 6), 7 - 8 * 9];
|
||||||
|
let a_expected = Point4::new(1 + 2, 2 * 3, 4 * f(5 + 6), 7 - 8 * 9);
|
||||||
|
assert_eq_and_type!(a, a_expected);
|
||||||
|
}
|
||||||
|
|
||||||
#[rustfmt::skip]
|
#[rustfmt::skip]
|
||||||
#[test]
|
#[test]
|
||||||
fn dvector_arbitrary_expressions() {
|
fn dvector_arbitrary_expressions() {
|
||||||
|
@ -137,7 +137,7 @@ pub use crate::sparse::*;
|
|||||||
pub use base as core;
|
pub use base as core;
|
||||||
|
|
||||||
#[cfg(feature = "macros")]
|
#[cfg(feature = "macros")]
|
||||||
pub use nalgebra_macros::{dmatrix, dvector, matrix, vector};
|
pub use nalgebra_macros::{dmatrix, dvector, matrix, point, vector};
|
||||||
|
|
||||||
use simba::scalar::SupersetOf;
|
use simba::scalar::SupersetOf;
|
||||||
use std::cmp::{self, Ordering, PartialOrd};
|
use std::cmp::{self, Ordering, PartialOrd};
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
use nalgebra::{dmatrix, dvector, matrix, vector};
|
use nalgebra::{dmatrix, dvector, matrix, point, vector};
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn sanity_test() {
|
fn sanity_test() {
|
||||||
@ -6,6 +6,7 @@ fn sanity_test() {
|
|||||||
|
|
||||||
let _ = matrix![1, 2, 3; 4, 5, 6];
|
let _ = matrix![1, 2, 3; 4, 5, 6];
|
||||||
let _ = dmatrix![1, 2, 3; 4, 5, 6];
|
let _ = dmatrix![1, 2, 3; 4, 5, 6];
|
||||||
|
let _ = point![1, 2, 3, 4, 5, 6];
|
||||||
let _ = vector![1, 2, 3, 4, 5, 6];
|
let _ = vector![1, 2, 3, 4, 5, 6];
|
||||||
let _ = dvector![1, 2, 3, 4, 5, 6];
|
let _ = dvector![1, 2, 3, 4, 5, 6];
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user