Info
This question is locked. 편집하거나 답변을 올리려면 질문을 다시 여십시오.
Showing the error "Variable nDimes has an incorrect value"
조회 수: 14 (최근 30일)
이전 댓글 표시
For this problem your code will need to do the following:
- Accurately determine the number of each coin type present. Use variable names nDimes, nNickels, nQuarters, and nFiftyCents.
- Calculate the total $ value of coins present. Use variable name USD
The code:
testImageIdx = randi([1,3]);
testCoinImage = imread("testCoinImage" + testImageIdx + ".png");
imshow(testCoinImage);
title("Original Coin Image");
[testcoinMask, MaskedtestCoin] = segmentCoin(testCoinImage);
se = strel('disk', 20, 0);
testCoinMask = imfill(testcoinMask, 'holes');
testCoinMask = imerode(testcoinMask, se);
imgFilt = imgaussfilt(MaskedtestCoin, 0.5, 'Padding', "circular", 'FilterDomain', "frequency", 'FilterSize', 3);
faceEdgeMask = edge(imgFilt, "sobel", 0.05, "both");
faceEdgeMask(~testcoinMask) = false;
imshow(faceEdgeMask);
title("Edge Mask Detection for Valid Coins");
see = strel("disk", 25, 0);
fb = imfill(faceEdgeMask, "holes");
Bw2 = imdilate(fb, see);
validCoinMask = Bw2 & testcoinMask;
set = strel("disk", 2, 0);
validCoinMask = imdilate(validCoinMask, set);
montage({testcoinMask, validCoinMask});
title("testcoinMask vs ValidCoinMask");
coinSizes = regionprops("table", validCoinMask, "Area");
nDimes = coinSizes.Area < 1100;
nDimes = sum(nDimes);
nNickels = (coinSizes.Area > 1100 & coinSizes.Area < 2200);
nNickels = sum(nNickels);
nQuarters = (coinSizes.Area > 2200 & coinSizes.Area < 3200);
nQuarters = sum(nQuarters);
nFiftyCents = coinSizes.Area >= 3200;
nFiftyCents = sum(nFiftyCents);
USD = (nDimes * 0.10) + (nNickels * 0.05) + (nQuarters * 0.25) + (nFiftyCents * 0.50);
function [testcoinMask, MaskedtestCoin] = segmentCoin(X)
X = im2gray(X);
testcoinMask = im2gray(X) > 150;
radius = 12;
decomp = 4;
se = strel('disk', radius, decomp);
testcoinMask = imclose(testcoinMask, se);
MaskedtestCoin = X;
MaskedtestCoin(~testcoinMask) = 0;
end
채택된 답변
Cris LaPierre
2024년 8월 2일
편집: Cris LaPierre
2024년 8월 2일
Inspect the criteria you are using to determine nDimes. Your code finds 11 dimes in each image, which is incorrect.
댓글 수: 2
Cris LaPierre
2024년 8월 4일
편집: Cris LaPierre
2024년 8월 4일
I believe the issue you are having is that your mask is not the area of the coins. This makes it difficult when using area to distinguish between coin types. Here is the validCoinMask your code is creating:
I had to change the range of areas your code uses to identify the coins, and it still was getting some wrong because of this.
You want your mask to look like this (both are masks for test image 1).
추가 답변 (2개)
martin
2024년 8월 24일
편집: Walter Roberson
2024년 8월 31일
testImageIdx = randi([1,3])
testCoinImage = imread("testCoinImage"+testImageIdx+".png");
imshow(testCoinImage);
title("Original Coin Image");
[testcoinMask, MaskedtestCoin] = segmentCoin(testCoinImage);
% Shrink the coin mask to focus on the coin regions
se = strel('disk', 20, 0);
testcoinMask = imfill(testcoinMask, 'holes');
testcoinMask = imerode(testcoinMask, se);
% Apply Gaussian filter to the masked coin image
imgFilt = imgaussfilt(MaskedtestCoin, 0.5, 'Padding', 'circular', 'FilterDomain', 'frequency', 'FilterSize', 3);
faceEdgeMask = edge(imgFilt, 'sobel', 0.05, 'both');
% Eliminate edges outside the shrunken coin mask
faceEdgeMask(~testcoinMask) = false;
imshow(faceEdgeMask);
title("Edge Mask Detection for Valid Coins");
% Refine the edge mask and create valid coin mask
se_dilate = strel('disk', 25, 0);
fb = imfill(faceEdgeMask, 'holes');
Bw2 = imdilate(fb, se_dilate);
validCoinMask = Bw2 & testcoinMask;
se_final = strel('disk', 2, 0);
validCoinMask = imdilate(validCoinMask, se_final);
% Display comparison
montage({testcoinMask, validCoinMask});
title("testcoinMask vs ValidCoinMask");
% Count the number of each type of coin
coinSizes = regionprops('table', validCoinMask, 'Area');
nDimes = nnz(coinSizes.Area < 1100);
nNickels = nnz(coinSizes.Area >= 1100 & coinSizes.Area < 2200);
nQuarters = nnz(coinSizes.Area >= 2200 & coinSizes.Area < 3200);
nFiftyCents = nnz(coinSizes.Area >= 3200);
% Calculate the total USD value
USD = (nDimes * 0.10) + (nNickels * 0.05) + (nQuarters * 0.25) + (nFiftyCents * 0.50);
% Display the total value
disp(['Total USD Value: $', num2str(USD)]);
function [testcoinMask, MaskedtestCoin] = segmentCoin(X)
X = im2gray(X);
% Adjust the threshold value as needed
testcoinMask = X > 150;
% Refine mask with morphological operations
radius = 20; % Adjust this value if necessary
se = strel('disk', radius);
testcoinMask = imclose(testcoinMask, se);
testcoinMask = imfill(testcoinMask, 'holes');
MaskedtestCoin = X;
MaskedtestCoin(~testcoinMask) = 0;
end
댓글 수: 0
krishnaveni
2024년 8월 31일
testImageIdx = randi([1,3])
testCoinImage = imread("testCoinImage"+testImageIdx+".png");
% Display the original image
imshow(testCoinImage);
title("Original Coin Image");
% Segment the coin from the image
[testcoinMask, MaskedtestCoin] = segmentCoin(testCoinImage);
% Perform morphological operations on the mask
se = strel('disk', 20, 0);
testCoinMask = imfill(testcoinMask, 'holes');
testCoinMask = imerode(testCoinMask, se);
% Apply Gaussian filtering and edge detection
imgFilt = imgaussfilt(MaskedtestCoin, 0.5, 'Padding', "circular", 'FilterDomain', "frequency", 'FilterSize', 3);
faceEdgeMask = edge(imgFilt, "sobel", 0.05, "both");
% Apply the edge mask to the coin mask
faceEdgeMask(~testCoinMask) = false;
imshow(faceEdgeMask);
title("Edge Mask Detection for Valid Coins");
% Refine the edge mask
see = strel("disk", 25, 0);
fb = imfill(faceEdgeMask, "holes");
Bw2 = imdilate(fb, see);
% Create a valid coin mask
validCoinMask = Bw2 & testCoinMask;
set = strel("disk", 2, 0);
validCoinMask = imdilate(validCoinMask, set);
% Display the masks
montage({testCoinMask, validCoinMask});
title("testcoinMask vs ValidCoinMask");
% Calculate coin sizes and classify them
coinSizes = regionprops(validCoinMask, 'Area');
% Initialize counters
nDimes = 0;
nNickels = 0;
nQuarters = 0;
nFiftyCents = 0;
% Define area thresholds for different coins
areaThresholds = struct('Dime', [0, 1100], 'Nickel', [1100, 2200], 'Quarter', [2200, 3200], 'FiftyCent', [3200, Inf]);
% Classify coins based on area
for k = 1:length(coinSizes)
area = coinSizes(k).Area;
if area > areaThresholds.Dime(1) && area <= areaThresholds.Dime(2)
nDimes = nDimes + 1;
elseif area > areaThresholds.Nickel(1) && area <= areaThresholds.Nickel(2)
nNickels = nNickels + 1;
elseif area > areaThresholds.Quarter(1) && area <= areaThresholds.Quarter(2)
nQuarters = nQuarters + 1;
elseif area > areaThresholds.FiftyCent(1)
nFiftyCents = nFiftyCents + 1;
end
end
% Calculate total USD
USD = (nDimes * 0.10) + (nNickels * 0.05) + (nQuarters * 0.25) + (nFiftyCents * 0.50);
% Display results
disp(['Number of Dimes: ', num2str(nDimes)]);
disp(['Number of Nickels: ', num2str(nNickels)]);
disp(['Number of Quarters: ', num2str(nQuarters)]);
disp(['Number of Fifty Cents: ', num2str(nFiftyCents)]);
disp(['Total USD: $', num2str(USD)]);
% Function for segmenting coins
function [testcoinMask, MaskedtestCoin] = segmentCoin(X)
% Convert to grayscale
X = im2gray(X);
% Create a binary mask based on intensity
testcoinMask = X > 150;
radius = 12;
decomp = 4;
se = strel('disk', radius, decomp);
testcoinMask = imclose(testcoinMask, se);
% Mask the coin from the image
MaskedtestCoin = X;
MaskedtestCoin(~testcoinMask) = 0;
end
댓글 수: 0
This question is locked.
참고 항목
제품
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!