槑图秀秀 (初学JAVA第三篇)


前言

本次adalab项目主要是以学习图像处理算法方面。
主要知识点为数组。


一、图像处理是什么?

图像处理是指对图像进行分析、加工、和处理,使其满足视觉、心理或其他要求的技术。图像处理是信号处理在图像领域上的一个应用。目前大多数的图像均是以数字形式存储,因而图像处理很多情况下指数字图像处理。此外,基于光学理论的处理方法依然占有重要的地位。

图像处理是信号处理的子类,另外与计算机科学、人工智能等领域也有密切的关系。

传统的一维信号处理的方法和概念很多仍然可以直接应用在图像处理上,比如降噪、量化等。然而,图像属于二维信号,和一维信号相比,它有自己特殊的一面,处理的方式和角度也有所不同。

二、PS软件介绍

用户界面及特性

PS软件用户界面
基础功能:
逆时针和顺时针旋转、水平旋转、反相、绿屏抠图、卷积、裁剪、均衡化。

产品特性:
1.乡村滤镜
2.二值化
3.图片去色
4.马赛克
5.浮雕化

待开发特性:
1.放大镜(目前仍然有bug)
2.各种滤镜
3.美颜功能


三、项目难点介绍

1. 卷积

二维卷积

二维卷积是我们最常用的也是最重要的,图像的边缘计算和模糊等算法都是基于卷积操作的只不过是对应的不同计算,卷积滤波器不同。

在这里插入图片描述
这里的kernel就是卷积核,kernel_size的大小一般是(3, 3)、(5, 5)、(7、7)这里是奇数的原因是因为方便计算。

代码展示:

 /**
     * Method: 图片卷积
     *
     * @param source
     * @return
     */
    public GImage convolution(GImage source) {
        int[][] pixelArray = source.getPixelArray();
        int pixelOfPhotoHeight = pixelArray.length;
        int pixelOfPhotoWidth = pixelArray[0].length;
        int[][] newPixelArray = new int[pixelOfPhotoHeight][pixelOfPhotoWidth];
        for (int y = 0; y < pixelOfPhotoHeight; y++) {
            for (int x = 0; x < pixelOfPhotoWidth; x++) {
                newPixelArray[y][x] = getPixel(pixelArray, x, y);
            }
        }
        return new GImage(newPixelArray);
    }

    /**
     * Method: 获得图片卷积参数
     *
     * @param pixelArray
     * @param x
     * @param y
     * @return
     */
    private int getPixel(int[][] pixelArray, int x, int y) {
        int pixelOfPhotoHeight = pixelArray.length;
        int pixelOfPhotoWidth = pixelArray[0].length;

        int rSum = 0;
        int bSum = 0;
        int gSum = 0;
        int pixelCount = 0;        // 计算卷积时,使用的像素点数

        int xMin = Math.max(x - CONVOLUTION_RADIUS, 0);
        int xMax = Math.min(x + CONVOLUTION_RADIUS, pixelOfPhotoWidth - 1);
        int yMin = Math.max(y - CONVOLUTION_RADIUS, 0);
        int yMax = Math.min(y + CONVOLUTION_RADIUS, pixelOfPhotoHeight - 1);

        for (int row = yMin; row <= yMax; row++) {
            for (int col = xMin; col <= xMax; col++) {
                int pixel = pixelArray[row][col];
                rSum += GImage.getRed(pixel);
                bSum += GImage.getBlue(pixel);
                gSum += GImage.getGreen(pixel);
                pixelCount++;
                System.out.println(row + " " + col + " " + pixelCount);
            }
        }
        return GImage.createRGBPixel(rSum / pixelCount, gSum / pixelCount, bSum / pixelCount);
    }

主要步骤:
通过长度为1的卷积半径来获取周围的像素点,再通过计算图片中当前像素点和周围像素点相加的rgb像素值,再除以总像素点(一般为9个像素点)实现卷积效果

2.图片均衡化

均衡化是一种主要应用于灰度照片的图像处理算法,可以增强画面对比度。

均衡化效果(如下):
在这里插入图片描述
代码如下:

/**
     * Method: 均衡化
     *
     * @param source
     * @return
     */
    public GImage equalization(GImage source) {
        int[] luminosityStatus = getLuminosityStatus(source);
        int[][] pixelArray = source.getPixelArray();
        int pixelOfPhotoHeight = pixelArray.length;
        int pixelOfPhotoWidth = pixelArray[0].length;

        for (int row = 0; row < pixelOfPhotoHeight; row++) {
            for (int col = 0; col < pixelOfPhotoWidth; col++) {
                int pixel = pixelArray[row][col];
                int r = GImage.getRed(pixel);
                int g = GImage.getGreen(pixel);
                int b = GImage.getBlue(pixel);
                int luminosity = computeLuminosity(r, g, b);
                int totalNumOfPixel = totalPixels(luminosityStatus, 0, luminosity + 1);
                int averageOfRGB = 255 * totalNumOfPixel / (pixelOfPhotoHeight * pixelOfPhotoWidth);
                int newImage = GImage.createRGBPixel(averageOfRGB, averageOfRGB, averageOfRGB);
                pixelArray[row][col] = newImage;
            }
        }
        return new GImage(pixelArray);
    }

    /**
     * Method: 获取当前像素点的亮度
     *
     * @param source
     * @return
     */
    private int[] getLuminosityStatus(GImage source) {
        int[][] pixelArray = source.getPixelArray();
        int pixelOfPhotoHeight = pixelArray.length;
        int pixelOfPhotoWidth = pixelArray[0].length;
        int[] luminosityStatus = new int[256];

        for (int row = 0; row < pixelOfPhotoHeight; row++) {
            for (int col = 0; col < pixelOfPhotoWidth; col++) {
                int pixel = pixelArray[row][col];
                int r = GImage.getRed(pixel);
                int g = GImage.getGreen(pixel);
                int b = GImage.getBlue(pixel);
                int luminosity = computeLuminosity(r, g, b);
                luminosityStatus[luminosity] += 1;
            }
        }
        return luminosityStatus;
    }

    /**
     * Method: 所有像素点
     *
     * @param quantityOfPixel
     * @param beg
     * @param end
     * @return
     */
    private int totalPixels(int[] quantityOfPixel, int beg, int end) {
        int total = 0;

        for (int a = beg; a < end; a++) {
            total += quantityOfPixel[a];
        }
        return total;
    }

实现步骤

首先需要计算亮度

亮度算法:

/* 计算图片亮度 */
public default int computeLuminosity(int r, int g, int b) {
	return GMath.round(0.299 * r + 0.587 * g + 0.114 * b);

使用方式:

int luminosity = computeLuminosity(red, green, blue);

然后调整颜色

调整颜色时,R、G、B三个通道会被调整为相等的值,都等于 255 * 亮度小于等于当前像素的像素个数 / 整张图片的像素数量 ,小数结果向下取整即可。


总结

图像处理项目让我初步了解算法知识和数组知识点,但我的主要问题还是无法独立完成项目,需要经常看别人代码和讲解才能一点一点摸出来。
总而言之,挤出时间学习java知识点以及学习好编程类英语知识,希望有一天能读懂英文Manual。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值