Date Validation Logic and Error message

조회 수: 4 (최근 30일)
Jack Crespo
Jack Crespo 2019년 3월 31일
댓글: akhil soni 2020년 9월 5일
I need help with writing a date validater in matlab without using built in time and date functions. It must check if a year is a leap year, and if so if february has no more than 29 days, and the other months satisfy their specific day maximums. If it isnt a leap year, then it checks if february has no more than 28 days, and the other months satisfy their specific day maximums. I have questions regarding checking if a year is a leap year and a new error message i have been getting.
1) Is my logic for checking for leap years correct? I used variables year1, year2, and year3 as assignments for the values of the year intputed divided by 4, 100, and 400, respectively. I then check if these values are evenly divided with the isfloat function. What would the correct logic look like?
2) I have been getting the error message "Output argument "valid" (and maybe others) not assigned during call to "valid_date"." What sources in my code could spark this error? I suspect i am overwriting the variable somehwere in my logic. I have done research to determine what this means and possible problems in the code and how to fix them, but I cannot for my life figure out what is causing the problem in my code.
I appreciate any comments. Please help because if have listened to every AC/DC album twice over while working on this code and i shouldnt have gray hair at 16 years old. I apoligize in advance for the quite messy code.
Thanks
function valid = valid_date(year, month, day)
year1 = year/4;
year2 = year/100;
year3 = year/400;
if isscalar(year) && year>=1 && isscalar(month) && month>=1 && month<=12 && isscalar(day) && day>=1 &&day<=31
if (~isfloat(year1) && ~isfloat(year2) && ~isfloat(year3)) || (~isfloat(year1) && isfloat(year2))
if month == 2
if day<=29
valid = true;
else
valid = false;
end
elseif month == 1 || month==3 || month==5 || month==7 || month==8 || month==10 || month==12
if day<=31
valid = true;
else
valid=false;
end
elseif month == 4 || month==6 || month==9 || month==11
if day <=30
valid=true;
else
valid=false;
end
else
valid=false;
end
else
if month <= 12
if month == 2 && day <=28
valid=true;
elseif month==1 || month==3 || month==5 || month==7 || month==8 || month==10 || month==12
if day > 31
valid = false;
else
valid=true;
end
else
if month == 4 || month==6 || month==9 || month==11
if day >30
valid=false;
else
valid=true;
end
end
end
else
valid=false;
end
end
else
valid = false;
end
end
  댓글 수: 5
Walter Roberson
Walter Roberson 2020년 2월 14일
You should not really be processing year to determine leap-year status until you have validated that year is a scalar positive integer.
akhil soni
akhil soni 2020년 9월 5일
function valid = valid_date(year,month,day)
if (isscalar(year)==1 && isscalar(month)==1 && isscalar(day)==1)
if (month>12 || date>31)
valid=false;
else
if ((month==1||month==3||month==5||month==7||month==9||month==11) && (day>0 && day<32))
valid=true;
elseif ((month==4||month==6||month==8||month==10||month==12) && (day>0 && day<31))
valid=true;
elseif (month==2 && (year/400==fix(year/400)) && (day>0 && day<30))
valid=true;
elseif (month==2 && ((year/100==fix(year/100))&&(year/400~=fix(year/400))) && (day>0 && day<29))
valid=true;
elseif (month==2 && (year/100~=fix(year/100)) && (year/400~=fix(year/400)) && (year/400==fix(year/400)) && (day>0 && day<30))
valid=true;
else valid=false;
end
end
else valid=false;
end
end
% I have done this but error is shown in line 3 stating:- Operands to the || and && operators must be convertible to logical scalar values.
%what does this means?

댓글을 달려면 로그인하십시오.

답변 (4개)

Neelkant Newra
Neelkant Newra 2020년 2월 14일
function valid = valid_date(year, month, day)
th31=[1,3,5,7,8,10,12];
th30=[4,6,9,11];
if isscalar(year) && year>=1 && isscalar(month) && month>=1 && month<=12 && isscalar(day) && day>=1 &&day<=31
if month == 2
if year/4 == fix(year/4)
if year/100 == fix(year/100) && year/400 == fix(year/400)
if day<=29
valid=true;
else
valid=false;
end
elseif year/100 == fix(year/100) && year/400 ~=fix(year/400)
if day <=28
valid = true;
else
valid = false;
end
else
if day <=29
valid = true;
else
valid =false;
end
end
else
if day<=28
valid= true;
else
valid=false;
end
end
elseif ismember(month,th31)
if day<=31
valid= true;
else
valid = false;
end
elseif ismember(month,th30)
if day<=30
valid = true;
else
valid = false;
end
end
else
valid= false;
end
  댓글 수: 1
Walter Roberson
Walter Roberson 2020년 2월 14일
No point in figuring out whether you are dealing with a leap year unless you have been asked to validate 29th day of 2nd month.

댓글을 달려면 로그인하십시오.


Rohan Singla
Rohan Singla 2020년 4월 23일
function isvalid = valid_date(y, m, d)
% Check if the inputs are valid %
Check that they are scalars
if ~(isscalar(y) && isscalar(m) && isscalar(d))
isvalid = false;
% Check that inputs are positive
elseif ~all([y, m, d] > 0)
isvalid = false;
% Check that inputs are integers (not the data type)
elseif any(rem([y, m, d], 1))
isvalid = false;
% Check that m and d are below the max possible
elseif (m > 12) || (d > 31) isvalid = false;
% The inputs could be a valid date, let's see if they actually are
else
% Vector of the number of days for each month
daysInMonth = [31 28 31 30 31 30 31 31 30 31 30 31];
% If leap year, change days in Feb
if isequal(rem(y, 4), 0) && (~isequal(rem(y, 100), 0) || isequal(rem(y, 400), 0))
daysInMonth(2) = 29;
end
maxDay = daysInMonth(m);
if d > maxDay
isvalid = false;
else
isvalid = true;
end
end
end

Arafat Roney
Arafat Roney 2020년 5월 11일
function valid=valid_date(year,month,day)
if((isscalar(year))&&(isscalar(month))&&(isscalar(day)))
if((year==abs(fix(year)))&&(isscalar(year)))
y=true;
else y=false;
end
if((month<=12)&&(month==abs(fix(month)))&&(month>0)&&(isscalar(month)))
m=true;
else m=false;
end
if((rem(year,4)==0)&&(rem(year,100)~=0)&&(rem(year,400)~=0)||(rem(year,100)==0)&&...
(rem(year,400)==0))
feb=29;
else
feb=28;
end
if(((month==4)||(month==6)||(month==9)||(month==11))&&(day<=30)&&(day>0)&&(day==abs(fix(day)))&&(isscalar(day)))
d=true;
elseif((((month==1)||(month==3)||(month==5)||(month==7))||(month==8)||...
(month==10)||(month==12))&&(day<=31)&&(day>0)&&(day==abs(fix(day)))&&(isscalar(day)))
d=true;
elseif((feb==28)&&(month==2)&&(day<=28)&&(day>0)&&(day==abs(fix(day)))&&(isscalar(day)))
d=true;
elseif((feb==29)&&(month==2)&&(day<=29)&&(day>0)&&(day==abs(fix(day)))&&(isscalar(day)))
d=true;
else d=false;
end
if((y==true)&&(m==true)&&(d==true))
valid=true;
else
valid=false;
end
else
valid=false;
end
end
  댓글 수: 1
Walter Roberson
Walter Roberson 2020년 5월 12일
If the year is non-scalar, then (year==abs(fix(year)) will be non-scalar, and you will have non-scalar && scalar which is an error. You need to test for scalar first.

댓글을 달려면 로그인하십시오.


Tahsin Oishee
Tahsin Oishee 2020년 5월 13일
function valid = valid_date(y,m,d)
if ~isscalar(y) && ~isscalar(m) && ~isscalar(d)
valid=false;
end
if y>0 && m>0 && m<12 && d>0 && d<31
valid=true;
else valid=false;
end
if m==1 && d==31
valid=true;
elseif m==3 && d==31
valid=true;
elseif m==4 && d>30
valid=false;
elseif m==5 && d==31
valid=true;
elseif m==6 && d>30
valid=false;
elseif m==7 && d==31
valid=true;
elseif m==8 && d==31
valid=true;
elseif m==9 && d>30
valid=false;
elseif m==10 && d==31
valid=true;
elseif m==11 && d>30
valid=false;
elseif m==12 && d==31
valid=true;
end
if m==2 && d==30 || d==31
valid=false;
end
if m==2 && rem(y,4)==0 && rem(y,100)~=0 && rem(y,400)~=0 && d==29
valid=true;
elseif m==2 && rem(y,100)==0 && rem(y,400)==0 && d==29
valid=true;
else valid=false;
end
end
  댓글 수: 1
Walter Roberson
Walter Roberson 2020년 5월 13일
편집: Walter Roberson 2020년 5월 13일
Suppose y is not scalar but m and d are scalar. ~isscalar(y) would be true, but ~isscalar(m) would be false, and true && false is false, so you would not set valid=false.
Now suppose that y, m, and d are all not scalar, then ~isscalar(y) && ~isscalar(m) && ~isscalar(d) is true, so you set valid=false. But then regardless you go on to test y>0 && m>0 and so on, which would be testing the non-scalar values and using && between the tests, which is going to be an error.
Now suppose y is -7 and m = 1 and d = 31, then y > 0 is false so y>0 && m>0 && m<12 && d>0 && d<31 is false so you set valid=false. But then you go into the if/elseif tree and m==1 && d==31 is true so you set valid=true even though the year is invalid.
Generally speaking, you should set up valid=true at the beginning, and then do tests rejecting cases by setting valid=false, and as soon as you get one valid=false then you can skip the rest of the tests.

댓글을 달려면 로그인하십시오.

카테고리

Help CenterFile Exchange에서 Dates and Time에 대해 자세히 알아보기

제품


릴리스

R2018b

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by