pgm二进制文件操作中的扭曲图像 [英] distorted image in pgm binary file manipulation

查看:225
本文介绍了pgm二进制文件操作中的扭曲图像的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试在 pgm 图片上执行卷积,类型为 P5 binary
,设置如下:



输入和输出数组

 矢量<矢量<炭>> image(rows,vector< char>(cols,'\ 0')); 
vector< vector< char>> out(rows,vector< char>(cols,'\ 0'));

const int SIZE = 3;

过滤器

 矢量<矢量< INT>> filter = {{0,-1,0},{-1,5,-1},{0,-1,0}}; 

将二进制数据插入图像数组



我正在读这样的PGM文件:

  getline(infile,type); 
// getline(infile,comment);
infile>>行>>的cols;
getline(infile,line);
getline(infile,最高);
// getline(infile,line);

for(int i = 0; i< rows; i ++)
for(int j = 0; j< cols; j ++)
infile>>图像[i] [j]; // infile来自filestream


outfile.open(output.pgm);

//将默认标头属性插入输出pgm文件。
outfile<<类型<< \ n<<行<< << cols<< \ n<< maxpx<< \\\
;


for(int i = SIZE / 2; i< rows - SIZE / 2; i ++)
{
for(int j = SIZE / 2; j< cols - SIZE / 2; j ++)
{
uint8_t sum = 0;
for(int k = -SIZE / 2; k< = SIZE / 2; k ++)
{
for(int l = -SIZE / 2; l< = SIZE / 2 ; l ++)
{
sum + = image [i + k] [j + l] * filter [k + SIZE / 2] [l + SIZE / 2];
}
}
out [i] [j] = sum;
}
}

将二进制数据写入输出文件

  for(int i = 0; i< rows; i ++)
for(int j = 0; j< cols; j ++ )
outfile<<出[i] [j];

运行代码时没有出现任何错误,但图像失真。我可以清楚地看出输出图像的某些部分,但它并没有完整。



不确定它是否与我的操作有关。



更新:



我将 uint8_t 更改为char,但我仍然得到同样的错误。


  1. 当我更改 outfile<< out [i] [j]; to outfile<< image [i] [j]; 所以我可以恢复实际图像,但看起来我可能会在将文件读入图像时出现一些问题矢量。不知道如何在这一点上。
    我得到这张图片

Lena.pgm文件



MCVE(Pastebin)

解决方案

我不是C ++方面的专家,但我相信你不能(或者可能不应该)使用>> 运算符来读取二进制文件。 / p>

我通过注意到你的图像在有黑色像素的地方出错而我认为这些空字节被 ifstream <错误地解释了/ code>当你根本不想让它们被解释时。我降低了图像的对比度,因此像素的范围不再是0-255而是67-197,这一切都有效。因此,当图像中没有低值时,它会起作用。



我认为您需要更改从以下位置读取二进制图像数据的方式:

  infile>>图像[i] [j]; 

类似于:

  infile.read((字符*)及图像[i] [j],1); 

或者使用 get()的东西。对不起,我不能更精确,因为C ++不是我的强项,但希望你现在可以继续前进。如果有人在评论中解释我在说什么 - 请随时教我!谢谢。


I'm trying to perform convolution on a pgm image of type P5 (binary) with the set up below:

input and output array

vector<vector<char>> image(rows, vector<char>(cols, '\0'));
vector<vector<char>> out(rows, vector<char>(cols, '\0'));

const int SIZE = 3;

Filter

vector<vector<int>> filter = { { 0, -1, 0 }, { -1, 5, -1 }, { 0, -1, 0 } };

insert binary data into image array

I'm reading PGM file like this:

getline(infile, type);
//getline(infile, comment);   
infile >> rows >> cols;   
getline(infile, line);
getline(infile, highest);    
//getline(infile, line);

for (int i = 0; i < rows; i++)
    for (int j = 0; j < cols; j++)
        infile >> image[i][j]; //infile is from filestream


outfile.open("output.pgm");

//Insert default header attributes into output pgm file.
outfile << type  << "\n" << rows << " " << cols << "\n" << maxpx << "\n";


    for (int i = SIZE / 2; i < rows - SIZE / 2; i++)
    {
        for (int j = SIZE / 2; j < cols - SIZE / 2; j++)
        {
            uint8_t sum = 0;
            for (int k = -SIZE / 2; k <= SIZE / 2; k++)
            {
                for (int l = -SIZE / 2; l <= SIZE / 2; l++)
                {
                    sum += image[i+k][j+l] * filter[k + SIZE / 2][l + SIZE / 2];
                }
            }
          out[i][j] = sum;
        }
    }

Write binary data into out file

for (int i = 0; i < rows; i++)
    for (int j = 0; j < cols; j++)
        outfile << out[i][j];

I do not get any error when I run the code, but the image is distorted. I can clearly make out some part of the output image, but it's is not coming out complete.

Not sure if it has to do with my manipulation.

Update:

I changed uint8_t to char, but I still get the same error.

  1. When I change outfile << out[i][j]; to outfile << image[i][j]; so I can get the actual image back, but looks like there could be some issues with how I'm reading the file into image vector. Not sure how to at this point. I get this image

Lena.pgm file

MCVE(Pastebin)

解决方案

I am no expert on C++, but I believe you cannot (or maybe should not) use the >> operator to read binary files.

I worked this out by noticing that your image goes wrong where there are black pixels and I believe that these null bytes are being interpreted incorrectly by ifstream when you don't actually want them interpreted at all. I decreased the contrast on your image so the range of the pixels was no longer 0-255 but 67-197 and it all works. So it works when there are no low values in your image.

I believe you need to change the way you read the binary image data from:

infile >> image[i][j];

to something like:

infile.read((char*)&image[i][j],1);

or maybe something using get(). Sorry, I cannot be more precise, as C++ is not my forte but hopefully you can now proceed further. If anyone cares to explain what I am saying in a comment - please feel free to teach me! Thank you.

这篇关于pgm二进制文件操作中的扭曲图像的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆