如果普通用for循环,用imageSharp的索引进行处理。测试图需要800毫秒。 用上ProcessPixelRows,只降低到平均720毫秒
而用bitmap.lock,然后用unsafe的byte*操作,只有125毫秒。 span是C#比较新版本,封装的对指针安全使用,效率与原生使用unsafe指针,看网上文章基本差不多。但为什么imageSharp ProcessPixelRows效率如此低?
我感觉应该代码写错了,但这就是照着官方demo写的,也没看出哪写的不对,请大佬指点了
如果普通用for循环,用imageSharp的索引进行处理
[C#] 纯文本查看 复制代码 SixLabors.ImageSharp.Image<Rgba32> oriImage = SixLabors.ImageSharp.Image.Load<Rgba32>(config.OriPicPath);
SixLabors.ImageSharp.Image<Rgba32> resultImage = SixLabors.ImageSharp.Image.Load<Rgba32>(config.ResultPicPath);
int width = oriImage.Width;
int height = oriImage.Height;
Rgba32 oriPixel;
Rgba32 resultPixel;
for (int x = 0; x < width; x++)
{
for (int y = 0; y < height; y++)
{
resultPixel = resultImage[x, y];
if (resultPixel.A > 0)
{
oriPixel = oriImage[x, y];
resultImage[x, y] = new Rgba32(oriPixel.R, oriPixel.G, oriPixel.B, resultPixel.A);
}
}
}
string newFilePath = Path.Combine(Path.GetDirectoryName(config.OriPicPath), Path.GetFileNameWithoutExtension(config.OriPicPath) + "_do" + Path.GetExtension(config.ResultPicPath));
FileStream fileStream = new FileStream(newFilePath, FileMode.Create);
PngEncoder pngEncoder = new PngEncoder();
resultImage.Save(fileStream, pngEncoder);
fileStream.Close();
然后是用上ProcessPixelRows
[C#] 纯文本查看 复制代码 SixLabors.ImageSharp.Image<Rgba32> oriImage = SixLabors.ImageSharp.Image.Load<Rgba32>(config.OriPicPath);
SixLabors.ImageSharp.Image<Rgba32> resultImage = SixLabors.ImageSharp.Image.Load<Rgba32>(config.ResultPicPath);
int width = oriImage.Width;
int height = oriImage.Height;
resultImage.ProcessPixelRows(oriImage, (resultAccessor, oriAccessor) =>
{
for (int y = 0; y < height; y++)
{
Span<Rgba32> resultRow = resultAccessor.GetRowSpan(y);
Span<Rgba32> oriRow = oriAccessor.GetRowSpan(y);
for (int x = 0; x < width; x++)
{
ref Rgba32 resutPixel = ref resultRow[x];
if (resutPixel.A > 0)
{
ref Rgba32 oriPixel = ref oriRow[x];
resutPixel = new Rgba32(oriPixel.R, oriPixel.G, oriPixel.B, resutPixel.A);
}
}
}
});
string newFilePath = Path.Combine(Path.GetDirectoryName(config.OriPicPath), Path.GetFileNameWithoutExtension(config.OriPicPath) + "_do" + Path.GetExtension(config.ResultPicPath));
FileStream fileStream = new FileStream(newFilePath, FileMode.Create);
PngEncoder pngEncoder = new PngEncoder();
resultImage.Save(fileStream, pngEncoder);
fileStream.Close(); |