Reputation: 5795
I have a table 'Student', and several attributes - two of which are important in this particular problem. I need to make sure that any student with the classification (grade level) of 'junior' has between exactly 55 and 84 hours (credits).
Here's what I have have so far declaration-wise in Oracle (deleted unnecessary code):
CREATE TABLE Students (
id INTEGER,
name CHAR(10) NOT NULL,
classification CHAR(10) NOT NULL,
hours INTEGER,
gpa NUMBER(3,2) NOT NULL,
mentor INTEGER,
-- IC4:
-- To be classified as a 'junior', a student must have
-- completed between 55 and 84 hours (inclusive).
CONSTRAINT IC4 CHECK (classification != 'junior' AND (hours < 55 AND hours > 84))),
);
Oracle throws the error:
ERROR at line 23: ORA-00922: missing or invalid option
I am certain that I haven't formatted the constraint correctly, but my professor spent about 3 seconds on declarations and told us to figure it out for ourselves. I know 1-attribute constraints, but I don't know how to mix and match 2 attributes at the same time. Can someone help me out?
*Essentially in any other code it would look like nested if-statements:
if (classification == "junior") {
if (hours < 55 && hours > 84)
throwSomeError("Foolish!");
}
I just can't seem to translate that into SQL. My apologies if the spacing in this darn thing is bizarre, I can't get it to format to save my life.
Upvotes: 1
Views: 1032
Reputation: 191235
You have a trailing comma right at the end, and one too many closing brackets:
...84))),);
Unless you've cut something out before posting, which may be the case as the error references line 23 (but hopefully not as it's tricky to see a problem in code you can't see at all). What you have compiles if that becomes:
...84)));
But the condition is wrong anyway, as others have pointed out. One way of getting the result I think you want is:
...
CONSTRAINT IC4 CHECK (classification != 'junior' OR hours BETWEEN 55 AND 84)
);
The OR
means that the hours
check is only applied when the classification
is 'junior'
, and any other classification
is not restricted. (If you need different rules for different classifications, have a look at the very similar question Chris Saxon linked to in comments).
With some test data:
insert into students values (1, 'A', 'junior', 54, 1, 1); -- ORA-02290
insert into students values (2, 'B', 'junior', 55, 1, 1); -- OK
insert into students values (3, 'C', 'junior', 84, 1, 1); -- OK
insert into students values (4, 'D', 'junior', 85, 1, 1); -- ORA-02290
insert into students values (5, 'E', 'senior', 54, 1, 1); -- OK
insert into students values (6, 'F', 'senior', 55, 1, 1); -- OK
insert into students values (7, 'G', 'senior', 84, 1, 1); -- OK
insert into students values (8, 'H', 'senior', 85, 1, 1); -- OK
select * from students order by id;
ID NAME CLASSIFICATION HOURS GPA MENTOR
---- ---------- -------------- ----- --- ------
2 B junior 55 1.00 1
3 C junior 84 1.00 1
5 E senior 54 1.00 1
6 F senior 55 1.00 1
7 G senior 84 1.00 1
8 H senior 85 1.00 1
6 rows selected
BETWEEN
is inclusive, so this is the same as:
CONSTRAINT IC4 CHECK (classification != 'junior' OR (hours >= 55 AND hours <= 84))
You might also want a check constraint on classification
, particularly as this constraint is case-sensitive as it stands; or preferably have a separate classification
table and have a foreign key constraint on the column in this table. But that's probably out of your control for this assignment.
Upvotes: 1
Reputation: 74
If you want to check that 'junior' should have value between 55 to 84 then use below compilable code-
CREATE TABLE Students ( id INTEGER, name CHAR(10) NOT NULL, classification CHAR(10) NOT NULL, hours INTEGER, gpa NUMBER(3,2) NOT NULL, mentor INTEGER, -- IC4: -- To be classified as a 'junior', a student must have -- completed between 55 and 84 hours (inclusive). CONSTRAINT IC4 CHECK (classification = 'junior' AND (hours >= 55 AND hours <= 84))) ;
Upvotes: 0
Reputation: 62831
Seems like the logic in your constraint might be off. Hours could never be less than 55 and greater than 84. Try using OR:
CONSTRAINT IC4 CHECK (classification != 'junior' AND (hours < 55 OR hours > 84))
However, this doesn't ensure that when classification = 'junior' the hours are between 55 and 84. Try using this instead:
CONSTRAINT IC4 CHECK (classification = 'junior' AND hours >= 55 AND hours <= 84))
Good luck.
Upvotes: 0
Reputation: 14361
Could it be that hours
is allowed Null
and that CHECK
can't process field that allows Null
s..
So try making hours integer Not NULL
and give a default value if your deem..
Also your condition has a mismatch.. check on that too....
Upvotes: 0