摘自《数字图像处理》 冈萨雷斯
一、处理可变数量的输入和输出
利用nargin和nargout进行检测
T = testhv(4, 5) |
该函数体中使用nargin返回2,使用nargout返回1.
函数nargchk可用于一个M函数体中,以检测传递函数的参量数目是否正确。
msg = nargchk(low, high, number)
参量number介于low与high之间返回空矩阵,否则返回错误信息。通常可这样使用:
function G = testhv2(x, y, z)
...
error(nargchk(2, 3, nargin));
...
|
键入仅有一个输入变量的语句
testhv2(6);
将产生错误消息
Not enough input arguments
同时执行终止。
通常,写出具有可变数目的输入变量和输出变量的函数时十分有用的。这里,我们使用变量varargin和变量varargout。varargin和varargout鼻血使用小写形式。例如,
function [m, n] = testhv3(varargin)
将输入的变量数读取到函数testhv3中,而
function [varargout] = testhv4(m, n, p)
则通过函数testhv4返回输出的变量数。若函数testhv3有一个固定的输入变量x,后跟输入变量的可变数目,则调用
function [m, n] = testhv3(x, varargin)
函数时,会导致varargin由用户提供的第二个输入变量开始运行。varargout的情形与此类似。一个函数的输入变量和输出变量的个数是可变的。
当varargin用做一个函数的输入变量时,Matlab会将其置入一个单元数组中,该数组接受由用户输入的变量数。由于varargin是一个单元数组,所以此类配置的一个重要方面是对函数的调用可包括输入的混合集。例如,若我们要使用假设函数testhv3的代码来处理此项操作,则它能很好的接受输入的混合集,如
[m, n] = testhv3(f, [0 0.5 1.5], A, 'label');
其中,f是一幅图像,下一个变量时一个长度为3的行向量,A是一个矩阵,'label'是一个字符串。
二、亮度变换的另一个M函数
在这一节中,我们将开发一个计算如下变换功能的函数:负片变换、对数变换、gamma变换和对比度拉伸变换。选用这些变换是因为随后我们将用到它们。此外,我们将进一步说明编写亮度变换M函数所涉及的机理。在编写该函数时,我们将用到函数changeclass,其语法为:
g = changeclass(newclass, f)
function image = changeclass(class, varargin)
%CHANGECLASS changes the storage class of an image.
% I2 = CHANGECLASS(CLASS, I);
% RGB2 = CHANGECLASS(CLASS, RGB);
% BW2 = CHANGECLASS(CLASS, BW);
% X2 = CHANGECLASS(CLASS, X, 'indexed');
% Copyright 1993-2002 The MathWorks, Inc. Used with permission.
% $Revision: 1.2 $ $Date: 2003/02/19 22:09:58 $
switch class
case 'uint8'
image = im2uint8(varargin{:});
case 'uint16'
image = im2uint16(varargin{:});
case 'double'
image = im2double(varargin{:});
otherwise
error('Unsupported IPT data class.');
end
|
此函数将图象f转换成有参数newclass指定的类别,并输出图像g。newclass的有效值是'uint8', 'uint16', 和'double'。
function g = intrans(f, varargin)
%INTRANS Performs intensity (gray-level) transformations.
% G = INTRANS(F, 'neg') computes the negative of input image F.
%
% G = INTRANS(F, 'log', C, CLASS) computes C*log(1 + F) and
% multiplies the result by (positive) constant C. If the last two
% parameters are omitted, C defaults to 1. Because the log is used
% frequently to display Fourier spectra, parameter CLASS offers the
% option to specify the class of the output as 'uint8' or
% 'uint16'. If parameter CLASS is omitted, the output is of the
% same class as the input.
%
% G = INTRANS(F, 'gamma', GAM) performs a gamma transformation on
% the input image using parameter GAM (a required input).
%
% G = INTRANS(F, 'stretch', M, E) computes a contrast-stretching
% transformation using the expression 1./(1 + (M./(F +
% eps)).^E). Parameter M must be in the range [0, 1]. The default
% value for M is mean2(im2double(F)), and the default value for E
% is 4.
%
% For the 'neg', 'gamma', and 'stretch' transformations, double
% input images whose maximum value is greater than 1 are scaled
% first using MAT2GRAY. Other images are converted to double first
% using IM2DOUBLE. For the 'log' transformation, double images are
% transformed without being scaled; other images are converted to
% double first using IM2DOUBLE.
%
% The output is of the same class as the input, except if a
% different class is specified for the 'log' option.
% Copyright 2002-2004 R. C. Gonzalez, R. E. Woods, & S. L. Eddins
% Digital Image Processing Using MATLAB, Prentice-Hall, 2004
% $Revision: 1.7 $ $Date: 2003/10/13 00:45:53 $
% Verify the correct number of inputs.
error(nargchk(2, 4, nargin))
% Store the class of the input for use later.
classin = class(f);
% If the input is of class double, and it is outside the range
% [0, 1], and the specified transformation is not 'log', convert the
% input to the range [0, 1].
if strcmp(class(f), 'double') & max(f(:)) > 1 & ...
~strcmp(varargin{1}, 'log')
f = mat2gray(f);
else % Convert to double, regardless of class(f).
f = im2double(f);
end
% Determine the type of transformation specified.
method = varargin{1};
% Perform the intensity transformation specified.
switch method
case 'neg'
g = imcomplement(f);
case 'log'
if length(varargin) == 1
c = 1;
elseif length(varargin) == 2
c = varargin{2};
elseif length(varargin) == 3
c = varargin{2};
classin = varargin{3};
else
error('Incorrect number of inputs for the log option.')
end
g = c*(log(1 + double(f)));
case 'gamma'
if length(varargin) < 2
error('Not enough inputs for the gamma option.')
end
gam = varargin{2};
g = imadjust(f, [ ], [ ], gam);
case 'stretch'
if length(varargin) == 1
% Use defaults.
m = mean2(f);
E = 4.0;
elseif length(varargin) == 3
m = varargin{2};
E = varargin{3};
else error('Incorrect number of inputs for the stretch option.')
end
g = 1./(1 + (m./(f + eps)).^E);
otherwise
error('Unknown enhancement method.')
end
% Convert to the class of the input image.
g = changeclass(classin, g);
|
例3.3 函数intrans的说明
要说明函数intrans,我们可以利用下面的例子,左边为原始图,右边为经对比度拉伸后的图像。
>> f = imread('Fig0306(a)(bone-scan-GE).tif');
>> figure(1)
>> imshow(f)
>> g = intrans(f, 'stretch', mean2(im2double(f)), 0.9);
>> figure(2)
>> imshow(g)
|
三、亮度标度的M函数
当处理图像是,象素值域由负到正的现象是很普遍的。尽管在中间计算过程中没有问题,但当我们想利用8bit或16bit格式保存或查看一幅图像时,就会出现问题。在这种情况下,我们通常希望吧图像标度在全尺度,即最大范围[0, 255]或[0, 65535]。下列名为gscale的M函数可以实现此功能。此外,此函数能将输出映射到一个特定的范围。
function g = gscale(f, varargin)
%GSCALE Scales the intensity of the input image.
% G = GSCALE(F, 'full8') scales the intensities of F to the full
% 8-bit intensity range [0, 255]. This is the default if there is
% only one input argument.
%
% G = GSCALE(F, 'full16') scales the intensities of F to the full
% 16-bit intensity range [0, 65535].
%
% G = GSCALE(F, 'minmax', LOW, HIGH) scales the intensities of F to
% the range [LOW, HIGH]. These values must be provided, and they
% must be in the range [0, 1], independently of the class of the
% input. GSCALE performs any necessary scaling. If the input is of
% class double, and its values are not in the range [0, 1], then
% GSCALE scales it to this range before processing.
%
% The class of the output is the same as the class of the input.
% Copyright 2002-2004 R. C. Gonzalez, R. E. Woods, & S. L. Eddins
% Digital Image Processing Using MATLAB, Prentice-Hall, 2004
% $Revision: 1.5 $ $Date: 2003/11/21 14:36:09 $
if length(varargin) == 0 % If only one argument it must be f.
method = 'full8';
else
method = varargin{1};
end
if strcmp(class(f), 'double') & (max(f(:)) > 1 | min(f(:)) < 0)
f = mat2gray(f);
end
% Perform the specified scaling.
switch method
case 'full8'
g = im2uint8(mat2gray(double(f)));
case 'full16'
g = im2uint16(mat2gray(double(f)));
case 'minmax'
low = varargin{2}; high = varargin{3};
if low > 1 | low < 0 | high > 1 | high < 0
error('Parameters low and high must be in the range [0, 1].')
end
if strcmp(class(f), 'double')
low_in = min(f(:));
high_in = max(f(:));
elseif strcmp(class(f), 'uint8')
low_in = double(min(f(:)))./255;
high_in = double(max(f(:)))./255;
elseif strcmp(class(f), 'uint16')
low_in = double(min(f(:)))./65535;
high_in = double(max(f(:)))./65535;
end
% imadjust automatically matches the class of the input.
g = imadjust(f, [low_in high_in], [low high]);
otherwise
error('Unknown method.')
end
|
调用语法为:
g = gscale(f, method, low, high)
其中,f是将被标度的图像,method的有效值为'full8'和'full16',前者将输出标度为全范围[0, 255],后者将输出标度为全范围[0, 65535]。若使用这两个有效值之一,则可在两种变换中省略参数low与high。method的第三个有效值为'minmax',此时我们必须给出low与high在范围[0, 1]内的值。若选用的是'minmax',则映射的结果