whenver i insert this if statement inside a for loop, i get an error. Could someone please explain why? Much appreciated!
2 views (last 30 days)
Show older comments
if class(input(i))=='double'
in this case, i want to check if the value of input(i) in the string 'input' is a number
Moved and formatted from an answer by champions2015 about 6 hours ago (by per isakson)
Some things I now understand where I was going wrong; as suggested I changed the variable name, which explains why I was getting one of the errors. I am now trying to use the 'isdouble' as Cam mentioned, but seem to be getting the following error:
Error in dial (line 6)
if isdouble(message{i})
My entire function is as follows:
function output=dial(message)
letters={'ABC', 'DEF', 'GHI', 'JKL', 'MNO', 'PQRS', 'TUV', 'WXYZ'};
number=[];
for i=1:length(message)
if isdouble(message(i))
number(i)=message(i);
else
for j=1:length(letters)
if ~isempty(strfind(letters{j},message(i))) %this function creates an array
number(i)=j+1;
end
end
end
end
output=uint64(number);
end
The actual question I'm trying to answer is as follows:
Each number on telephone keypads, except 0 and 1, corresponds to a set of uppercase letters as shown in this list: 2 ABC, 3 DEF, 4 GHI, 5 JKL, 6 MNO, 7 PQRS, 8 TUV, 9 WXYZ Hence, a phone-number specification can include uppercase letters and digits. Write a function called dial that takes as its input argument a char vector of length 16 or less that includes only these characters and returns as its output argument the telephone number as a uint64. Here is the input and output for one example of a call of the function: Input: '1FUNDOG4YOU' Output: 13863644968 You can assume that a phone number never starts with 0. If the input contains any illegal characters, the function returns 0. You are not allowed to use the built-in function strrep.
Thanks again in advance!
Accepted Answer
per isakson
on 4 Sep 2017
Edited: per isakson
on 6 Sep 2017
Comments
- isdouble is a special function of the Fixed Point Toolbox.
- Your main problem is that you are not careful enough with the classes of the variables. E.g. "i want to check if the value of input(i) in the string 'input' is a number" input(i) is the i:th character of the string, input. "class(input(i))=='double'" will never be true. You really want to test whether input(i) is a digit. Furthermore, with number(i)=message(i); and number(i)=j+1; you try to first put characters then floating point numbers into number.
Proposals
- Make it a habit to use Debug a MATLAB Program and Examine Values While Debugging
- Debug and fix your function. E.g. rename number, because it is a confusing name of a string.
Try
>> out = dial('1FUNDOG4YOU')
out =
13863644968
>> out = dial('1zFUNDOG4YOU')
Warning: Illegal character in input: "z"
> In dial (line 17)
out =
0
where
function output = dial( str )
% (c) per isakson
%{
out = dial('1FUNDOG4YOU')
out = dial('1zFUNDOG4YOU')
%}
letters = {'ABC', 'DEF', 'GHI', 'JKL', 'MNO', 'PQRS', 'TUV', 'WXYZ'};
digits = {'2','3','4','5','6','7','8','9', '0','1' };
phone = repmat( '-', size(str) ); % pre-allocate a character string
for jj = 1:length(str)
if any( strcmp( str(jj), digits ) )
phone(jj) = str(jj);
elseif ismember( str(jj), strjoin(letters,'') )
pos = strfind( letters, str(jj) );
is = not( cellfun( @isempty, pos ) );
phone(jj) = digits{is};
else
warning( 'Illegal character in input: "%s"', str(jj) )
phone = '0';
break
end
end
output = sscanf( phone, '%lu' ); % or uint64(str2double(phone))
end
Don't turn in my entire function as your homework. It's obvious that you didn't make it. However, learn from it. Understand how it works with the help of the documentation. And copy and edit pieces of it.
An alternative in response to a comment
function out = dial(message)
letters = {'ABC', 'DEF', 'GHI', 'JKL', 'MNO', 'PQRS', 'TUV', 'WXYZ'};
Numbers = repmat( '-', size(message) );
digits = {'2','3','4','5','6','7','8','9','0','1'};
%
for i=1:length(message)
% any returns 1 if message(i) is a digit found in 'digits'
if ismember( message(i), digits )
Numbers(i)=message(i);
else
for j=1:length(letters)
if ismember( message(i), letters{j} )
ix = j;
break
end
ix = 0;
end
if ix >= 1
Numbers(i) = digits{ix};
else
Numbers = '0';
break
end
end
end
out = uint64(str2double(Numbers));
end
3 Comments
Walter Roberson
on 5 Sep 2017
Your code would be clearer if you used ismember() instead of strcmp and strfind
per isakson
on 6 Sep 2017
Edited: per isakson
on 6 Sep 2017
The logic of this piece of code is seriously flawed
for j=1:length(letters)
if ~isempty(strfind(letters{j},message(i)))
Numbers(i)=num2str(j+1);
else
Numbers=0;
return
end
end
For every letter, message(i), the else-clause will be executed resulting in an early return from the function.
- ~isempty(strfind(letters{j},message(i))) is hard to read and understand.
- "this function[sic] creates an array of 1 0 values if message(i) is in letters{j}" doesn't apply to your code(?) However, it's useful to write in words what you want the code to do, but it must be crystal clear and correct.
- Numbers =''; allocates an empty string.
More Answers (2)
Cam Salzberger
on 3 Sep 2017
Edited: Cam Salzberger
on 3 Sep 2017
As Stephen is probably indicating, the input argument to the input function needs to be a character vector. This is likely to be the error message you are getting:
Error using input
The first argument to INPUT must be a character vector.
Instead, I'd recommend getting the input, storing it to a variable, and then check the value. Otherwise you'll have no way to access the value later. Something like this:
inVal = input('Give me a number: ');
if ...check condition here...
...
end
Now, there are a few other issues here. Firstly, I would not recommend using "==" to compare two character vectors. You may get an error if they're not the same length, and you'll get a vector output otherwise. What you probably want to use is strcmp instead.
Secondly, you don't need to compare the output of "class", you can just use the isdouble function. This will be more efficient.
inVal = input('Give me a number: ');
if isdouble(inVal)
...
end
If you are trying to do "input(i)" because "input" is an array that you are trying to access into... don't. Don't overload built-in functions or constants with variable names. Pick a different variable to use.
Hope this helps.
-Cam
2 Comments
Steven Lord
on 5 Sep 2017
Note that isdouble is part of the Fixed-Point Designer product. For something similar that's in MATLAB itself, use isa(x, 'double').
See Also
Categories
Find more on Startup and Shutdown in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!