You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
After #909 w/ the move to remove unsafe code, I think (didn't test extensively) the implementation of copy_from got significantly slower. At the very least, it became a recent bottleneck for me that I spent some time looking at.
The implementation of copy_from is a pretty straight forward get_pixel/put_pixel loop over the image data where the function calls aren't inlined and are performing bounds checks on every access, even tho the preconditions of the function already do the bounds check beforehand.
In my specific case I managed to ~3x increase the performance, without re-introducing unsafe code, by copying over scanlines at a time. The code below lives in my project because I can live without it having to be a generalized implementation (as you see - it would need to be adapted to GenericImage/GenericImageView to be able to live in this project properly).
I'm submitting it here (rather then as a pull request) because I found a way to entirely not go down this code path at all anymore, however, I'm sharing it because I think it's useful to this project still and can potentially be adapted.
traitFastCopyFrom{typePixel: image::Pixel;fnfast_copy_from(&mutself,other:&image::RgbaImage,x:u32,y:u32);}implFastCopyFromfor image::RgbaImage{typePixel = <image::RgbaImageasGenericImageView>::Pixel;fnfast_copy_from(&mutself,other:&image::RgbaImage,x:u32,y:u32){// Do bounds checking here so we can use the non-bounds-checking// functions to copy pixels.ifself.width() < other.width() + x || self.height() < other.height() + y {return;}let other_data = other.as_raw();let self_w = self.width();letmut self_data = self.as_flat_samples_mut();letmut self_slice = self_data.as_mut_slice();let other_w = other.width();for k in0..other.height(){let other_start = ((k * other_w)*4)asusize;let other_end = (((k + 1)* other_w)*4)asusize;let self_start = (((x) + ((k + y)* self_w))*4)asusize;let self_end = self_start + (other_w *4)asusize;
self_slice[self_start..self_end].copy_from_slice(&other_data[other_start..other_end]);}}}
Timings before
Timings after
The text was updated successfully, but these errors were encountered:
After #909 w/ the move to remove unsafe code, I think (didn't test extensively) the implementation of
copy_from
got significantly slower. At the very least, it became a recent bottleneck for me that I spent some time looking at.The implementation of
copy_from
is a pretty straight forwardget_pixel
/put_pixel
loop over the image data where the function calls aren't inlined and are performing bounds checks on every access, even tho the preconditions of the function already do the bounds check beforehand.In my specific case I managed to ~3x increase the performance, without re-introducing unsafe code, by copying over scanlines at a time. The code below lives in my project because I can live without it having to be a generalized implementation (as you see - it would need to be adapted to
GenericImage
/GenericImageView
to be able to live in this project properly).I'm submitting it here (rather then as a pull request) because I found a way to entirely not go down this code path at all anymore, however, I'm sharing it because I think it's useful to this project still and can potentially be adapted.
Timings before
Timings after
The text was updated successfully, but these errors were encountered: