为什么这个图像阈值适用于 windows 但不适用于单声道/linux?
Why would this image threshold work in windows but not mono / linux?
我有一个使用不安全代码的相对简单的阈值函数。这在 Windows 中有效,但是,在 linux 上的 Mono 中,没有发生阈值。很难调试,因为它仅在 Linux 上,我检查过 bitsPerPixel 是否正确以及高度 h
、宽度 w
和步幅 ws
是否都正确.
我还能做些什么来缩小范围,或者这里有一个常见的问题吗?
public void threshold(Bitmap bmp, int thresh)
{
var bitsPerPixel = Image.GetPixelFormatSize(bmp.PixelFormat) / 8;
BitmapData bmData = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height),
ImageLockMode.ReadOnly, bmp.PixelFormat);
unsafe
{
byte* p = (byte*)(void*)bmData.Scan0.ToPointer();
int h = bmp.Height;
int w = bmp.Width;
int ws = bmData.Stride;
for (int i = 0; i < h; i++)
{
byte* row = &p[i * ws];
for (int j = 0; j < w * bitsPerPixel; j += bitsPerPixel)
{
for (var k = 0; k < bitsPerPixel; k++)
{
row[j + k] = (byte)((row[j + k] > (byte)thresh) ? 255 : 0);
}
}
}
}
bmp.UnlockBits(bmData);
}
将ImageLockMode
设置为ReadWrite
:
BitmapData bmData = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height),
ImageLockMode.ReadWrite, bmp.PixelFormat);
示例:
public unsafe void Threshold(Bitmap bmp, int thresh)
{
var bmData = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height), ImageLockMode.ReadWrite, bmp.PixelFormat);
var bitsPerPixel = Image.GetPixelFormatSize(bmp.PixelFormat);
var p = (byte*)bmData.Scan0.ToPointer();
for (int i = 0; i < bmData.Height; ++i)
{
for (int j = 0; j < bmData.Width; ++j)
{
byte* data = p + i * bmData.Stride + j * bitsPerPixel / 8;
data[0] = (byte)((data[0] > thresh) ? 255 : 0);
data[1] = (byte)((data[1] > thresh) ? 255 : 0);
data[2] = (byte)((data[2] > thresh) ? 255 : 0);
}
}
bmp.UnlockBits(bmData);
我有一个使用不安全代码的相对简单的阈值函数。这在 Windows 中有效,但是,在 linux 上的 Mono 中,没有发生阈值。很难调试,因为它仅在 Linux 上,我检查过 bitsPerPixel 是否正确以及高度 h
、宽度 w
和步幅 ws
是否都正确.
我还能做些什么来缩小范围,或者这里有一个常见的问题吗?
public void threshold(Bitmap bmp, int thresh)
{
var bitsPerPixel = Image.GetPixelFormatSize(bmp.PixelFormat) / 8;
BitmapData bmData = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height),
ImageLockMode.ReadOnly, bmp.PixelFormat);
unsafe
{
byte* p = (byte*)(void*)bmData.Scan0.ToPointer();
int h = bmp.Height;
int w = bmp.Width;
int ws = bmData.Stride;
for (int i = 0; i < h; i++)
{
byte* row = &p[i * ws];
for (int j = 0; j < w * bitsPerPixel; j += bitsPerPixel)
{
for (var k = 0; k < bitsPerPixel; k++)
{
row[j + k] = (byte)((row[j + k] > (byte)thresh) ? 255 : 0);
}
}
}
}
bmp.UnlockBits(bmData);
}
将ImageLockMode
设置为ReadWrite
:
BitmapData bmData = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height),
ImageLockMode.ReadWrite, bmp.PixelFormat);
示例:
public unsafe void Threshold(Bitmap bmp, int thresh)
{
var bmData = bmp.LockBits(new Rectangle(0, 0, bmp.Width, bmp.Height), ImageLockMode.ReadWrite, bmp.PixelFormat);
var bitsPerPixel = Image.GetPixelFormatSize(bmp.PixelFormat);
var p = (byte*)bmData.Scan0.ToPointer();
for (int i = 0; i < bmData.Height; ++i)
{
for (int j = 0; j < bmData.Width; ++j)
{
byte* data = p + i * bmData.Stride + j * bitsPerPixel / 8;
data[0] = (byte)((data[0] > thresh) ? 255 : 0);
data[1] = (byte)((data[1] > thresh) ? 255 : 0);
data[2] = (byte)((data[2] > thresh) ? 255 : 0);
}
}
bmp.UnlockBits(bmData);