【问题标题】:convert image to byte Matrix将图像转换为字节矩阵
【发布时间】:2018-08-06 09:03:52
【问题描述】:

我正在尝试对图像(png)进行二值化以获得以下结果:

为此,我使用以下代码,但现在我没有预期的结果:

这给了我以下结果enter image description here

【问题讨论】:

  • 不要链接图片,不要将代码发布为图片。
  • 看起来你的零线比你想要的长得多。我想如果您在右侧文本框中添加滚动条,您可以向下滚动以查看文本的 1s 部分。您可能只需要在文本区域中添加水平和垂直文本栏。

标签: c# image binary-data


【解决方案1】:

你可以这样做,它使用扫描线和锁定位,而且速度相当快。

public unsafe static int[,] GetBits(string path )
{
   using (var orig = new Bitmap(path))
   {
      var bounds = new Rectangle(0, 0, orig.Width, orig.Height);    
      // lock the array for direct access
      var bitmapData = orig.LockBits(bounds, ImageLockMode.ReadWrite, PixelFormat.Format32bppPArgb);

      try
      {
         // get the pointer
         var scan0Ptr = (int*)bitmapData.Scan0;    
         // get the stride
         var stride = bitmapData.Stride / 4;    
         // keep the black around
         var black = Color.Black.ToArgb();    
         //Output
         var array = new int[orig.Width, orig.Height];

         // scan all x first then y
         for (var y = 0; y < bounds.Bottom; y++)
            for (var x = 0; x < bounds.Right; x++)                     
               array[x, y] = *(scan0Ptr + x + y * stride) == black ? 0 : 1;

         return array;    
      }
      finally
      {
         // unlock the bitmap
         orig.UnlockBits(bitmapData);
      }    
   }
}

用法

var array = GetBits(@"d:\icon.png");

var w = array.GetLength(0);
var h = array.GetLength(1);

for (int i = 0; i < w; i++)
{
   for (int j = 0; j < h; j++)
      Console.Write(array[i,j]);
   Console.WriteLine();
}

输出

00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
00011111111111111111111111111000
00011111111111111111111111111000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000000000000000011000
00011000000000011111111111111000
00011000000000011111111111111000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011000000000011000000000011000
00011111111111111111111111111000
00011111111111111111111111111000
00000000000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000

原始图像 32x32

【讨论】:

    【解决方案2】:

    要比较两种颜色,请使用ToArgb 方法,最好使用StringBuilder,而不是每次都连接。
    这对我有用:

    var img = new Bitmap(pictureBox1.Image);
    var sb = new StringBuilder();
    
    for (int i = 0; i < img.Height; i++)
    {
        for (int j = 0; j < img.Width; j++)
        {
            if (img.GetPixel(j, i).ToArgb() == Color.White.ToArgb())
            {
                sb.Append("0");
            }
            else
            {
                sb.Append("1");
            }
        }
    }
    
    richTextBox1.Text = sb.ToString();
    

    这会导致很多零和一些零,我的图片很大,所以结果很难看,但在你的情况下它应该可以工作。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-01-03
      相关资源
      最近更新 更多