如何用Python将RGB图像转换为灰度图像

526 阅读6分钟

为了开始,导入 cv2模块,它将提供读取原始图像并将其转换成灰度所需的功能。我们将使用argparse模块通过命令行传递图像,然后它将把图像转换成灰度。

Python RGB图像转灰度

要在Python RGB 图像转换成灰度 ,可以使用cv2.imread(args["image"])和cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) 方法。

首先,我们必须安装opencv-python包。你可以用下面的命令来安装它:

python3 -m pip install opencv-python

# OR

pip install opencv-python

要将RGB图像转换为灰度,请按照以下步骤进行:

  1. 导入所需的模块
  2. 定义一个灰度转换函数
  3. 使用argparse模块获取输入图像。

第一步:导入所需模块

我们将使用PIL模块中的图像对象。所以我们要特别导入这个模块。

然后导入argparse模块。然后,再导入cv2模块和os模块:

# app.py

import argparse
import cv2
import os

第二步:定义一个灰度函数。

我们将在这个函数中使用cv2.imread()方法读取图像。

为了简单起见,我们假设文件存在,并且一切加载正常,所以我们将不做任何错误或异常检查。

尽管如此,你应该处理这些类型的异常,以实现强大的代码。否则你会陷入麻烦。

请看下面的代码:

# Function to convert RGB Image to GrayScale
def convertImageToGray(args):
    image = cv2.imread(args["image"])
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    filename = f"{os.getpid()}.png"
    cv2.imwrite(filename, gray)
    print('The image is converted to Grayscale successfully')

你可以看到,我们定义了一个名为**convertImageToGray()**方法的函数。

该函数将args作为一个参数。这个参数包含我们需要转换为灰度的图像。

作为一个额外的说明,这对于转换为灰度是必要的,imread()函数的通道默认是以BGR (蓝、绿、红)的顺序存储的。

接下来,我们需要将图像解析为灰度。要做到这一点,我们必须调用**cvtColor()**函数,它允许我们将图像从一个颜色空间转换到另一个颜色空间。

作为第一个输入,这个函数接收原始图像。作为第二个输入,它得到颜色空间转换代码。由于我们要将原始RGB图像从BGR色彩空间转换为灰色,我们使用代码COLOR_BGR2GRAY

让我们进入最后一步。

第三步:获取输入图像

在app.py文件内添加以下代码:

# Fetch the arguments from the command line
ap = argparse.ArgumentParser()
ap.add_argument("-i", "--image", required=True,
                help="path to input image")
args = vars(ap.parse_args())

我们的命令行参数被解析了。我们有以下的命令行参数。

  1. -图像:我们要发送给函数的图像的路径。

因此,当我们运行命令python3 app.py时,我们传递给图像的参数路径,如下所示。

python3 app.py --image="data.jpg"

这里,data.jpg图片被传递给**convertImageToGray()**方法。

最后,调用该函数。

所以,我们的最终代码看起来像下面这样。

import argparse
import cv2
import os

# Function to convert RGB Image to GrayScale
def convertImageToGray(args):
    image = cv2.imread(args["image"])
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    filename = f"{os.getpid()}.png"
    cv2.imwrite(filename, gray)
    print('The image is converted to Grayscale successfully')


# Fetch the arguments from the command line
ap = argparse.ArgumentParser()
ap.add_argument("-i", "--image", required=True,
                help="path to input image")
args = vars(ap.parse_args())

# Call the convertImageToGray() Function
filename = convertImageToGray(args)

这就是了,现在,到终端输入以下命令,并输入图像路径。

python3 app.py --image="data.jpg"

你可以检查你当前的项目文件夹,寻找一个图像名称,如4999.png或任何四位数的数字.png图像。我的图像在下面输出的右边。 请看下面的输出。

How to Convert RGB Image to Grayscale in Python

应用阈值对图像进行预处理

到目前为止,在命令的时候,我们只传递了一个参数,叫做-image。

现在,我们将传递另一个参数,叫做preprocess,其值是以下两个中的一个:

  1. 阈值
  2. 模糊

我们可以检查是否应该应用阈值处理来预处理图像,否则就进行检查,看是否应该进行中值模糊处理来去除噪声。

请看下面的代码:

import argparse
import cv2
import os

# Function to convert Normal Image to GrayScale
def convertImageToGray(args):
    image = cv2.imread(args["image"])
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)

    # check to see if we should apply thresholding to preprocess the image
    if args["preprocess"] == "thresh":
        gray = cv2.threshold(gray, 0, 255,
                             cv2.THRESH_BINARY | cv2.THRESH_OTSU)[1]

    # check to see if median blurring should be done to remove noise
    elif args["preprocess"] == "blur":
        gray = cv2.medianBlur(gray, 3)

    # write the grayscale image to disk as a temporary file.
    filename = f"{os.getpid()}.png"
    cv2.imwrite(filename, gray)
    print('The image is converted to Grayscale successfully')


# Fetch the arguments from the command line
ap = argparse.ArgumentParser()
ap.add_argument("-i", "--image", required=True,
                help="path to input image to be OCR'd")
ap.add_argument("-p", "--preprocess", type=str, default="thresh",
                help="type of preprocessing to be done")
args = vars(ap.parse_args())

# Call the convertImageToGray() Function
filename = convertImageToGray(args)

现在输入以下命令:

python3 app.py --image="data.jpg" --preprocess="thresh"

输出

Convert RGB to graycscale with threshold

我们将根据我们的命令行参数指定的预处理方法,对图像进行阈值处理或模糊处理。这就是你要添加更高级的预处理方法的地方。

函数内部的if语句执行一个阈值,将前景和背景分开。我们使用cv2.THRESH_BINARYcv2.THRESH_OTSU 这两个标志来做这个。

关于大津方法的细节,请参见OpenCV官方文档中的 "大津的二值化"。

另外,也可以应用一种模糊方法。当-preprocess标志被设置为模糊时,将应用中值模糊。应用中值模糊可以帮助减少盐和胡椒的噪音。这种过滤器对于使用Tesseract对图像进行正确的OCR非常有用。

我们还可以使用cv2模块以编程方式打开RGB图像和灰度图像。

你只需在函数中添加以下代码就可以打开这两种图像:

cv2.imshow('Original image',image)
cv2.imshow('Gray image', gray)
cv2.waitKey(0)
cv2.destroyAllWindows()

为了显示图像,我们必须调用cv2模块的imshow()函数。

cv2.imshow()函数的第一个输入是要分配给窗口的名称的字符串,第二个参数是要显示的图像。

我们将显示两张图像,以比较转换后的图像和原始图像。

最后,我们将调用waitKey() 方法,它将等待一个键盘事件。

waitKey()方法的输入是延迟,以毫秒为单位。尽管如此,如果我们传递的值是0,它将无限期地等待,直到一个按键事件发生。

最后,一旦用户按下按键,我们就调用**destroyAllWindows()**函数,它将销毁之前创建的窗口。

请看完整的代码:

import argparse
import cv2
import os

# Function to convert Normal Image to GrayScale
def convertImageToGray(args):
    image = cv2.imread(args["image"])
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)

    # check to see if we should apply thresholding to preprocess the image
    if args["preprocess"] == "thresh":
        gray = cv2.threshold(gray, 0, 255,
                             cv2.THRESH_BINARY | cv2.THRESH_OTSU)[1]

    # check to see if median blurring should be done to remove noise
    elif args["preprocess"] == "blur":
        gray = cv2.medianBlur(gray, 3)

    # write the grayscale image to disk as a temporary file.
    filename = f"{os.getpid()}.png"
    cv2.imwrite(filename, gray)
    print('The image is converted to Grayscale successfully')
    cv2.imshow('Original image', image)
    cv2.imshow('Gray image', gray)
    cv2.waitKey(0)
    cv2.destroyAllWindows()


# Fetch the arguments from the command line
ap = argparse.ArgumentParser()
ap.add_argument("-i", "--image", required=True,
                help="path to input image to be OCR'd")
ap.add_argument("-p", "--preprocess", type=str, default="thresh",
                help="type of preprocessing to be done")
args = vars(ap.parse_args())

# Call the convertImageToGray() Function
filename = convertImageToGray(args)

现在,输入以下命令:

python3 app.py --image="data.jpg" --preprocess="thresh"

总结

我们为动态图像转换创建了这个教程。所以你可以输入任何你想要的路径,使用Python中的argparse模块将该图像转换为灰度。

本教程就到此为止。