Joseph said:
There is no way I can think of to limit the number of ROWS
You can test for the presence of 'line feed' characters. If you could
assume that all line feeds are vbCrLf then things would be easy. Of
course, you can't make this assumption and handling all the possible
combinations quickly becomes messy.
As I see it the combinations are CHR$(13) & CHR$(10) and CHR$(10);
however, you cannot rule out CHR$(13) only, and, for completeness,
CHR$(10) & CHR$(13). Because the OP's requirement is to allow up to
five lines, then we have to test a lot of combinations.
A replace function would come in handy e.g. for each step replace a
'line' character (combination) with a known but unusual character e.g.
CHR$(22):
REPLACE$(Address, CHR$(10) & CHR$(13), CHR$(22))
REPLACE$(Address, CHR$(13) & CHR$(10), CHR$(22))
REPLACE$(Address, CHR$(13), CHR$(22))
REPLACE$(Address, CHR$(10), CHR$(22))
Then count the number of CHR$(22) characters
LEN(Address) - LEN(REPLACE$(Address, CHR$(22), ''))
Of course, instead of 'Address' above they should be nested like this
(untested):
LEN(REPLACE$(REPLACE$(REPLACE$(REPLACE$(Address, CHR$(10) & CHR$(13),
CHR$(22)), CHR$(13) & CHR$(10), CHR$(22)), CHR$(13), CHR$(22)),
CHR$(10), CHR$(22))) -
LEN(REPLACE$(REPLACE$(REPLACE$(REPLACE$(REPLACE$(Address, CHR$(10) &
CHR$(13), CHR$(22)), CHR$(13) & CHR$(10), CHR$(22)), CHR$(13),
CHR$(22)), CHR$(10), CHR$(22)), CHR$(22), ''))
See what I mean about messy <g>?
In the absence of a replace function all the combinations of 'line
feed' combinations and flavours of wildcard character could be tested,
with a separate validation rule for each e.g. here's one:
Address NOT LIKE '%' & CHR$(10) & '%' & CHR$(10) & '%' & CHR$(10) & '%'
& CHR$(10) & '%' & CHR$(10) & '%'
Allowing for both ANSI and non-ANSI flavours of wildcard character,
that just leaves 2047 other combinations to write ;-)
More practical would be to build up an auxiliary table of combinations.
First the line feeds:
CREATE TABLE LineFeeds (
line_feed VARCHAR(2) NOT NULL UNIQUE
);
INSERT INTO LineFeeds (line_feed) VALUES (CHR$(10) & CHR$(13));
INSERT INTO LineFeeds (line_feed) VALUES (CHR$(13) & CHR$(10));
INSERT INTO LineFeeds (line_feed) VALUES (CHR$(13));
INSERT INTO LineFeeds (line_feed) VALUES (CHR$(10));
Then create all the combinations (easy with a 'cartesian product') for
each wildcard character:
CREATE TABLE LineFeedPatterns (
line_feed_pattern VARCHAR(143) NOT NULL UNIQUE
)
;
INSERT INTO LineFeedPatterns (line_feed_pattern)
SELECT DT1.line_feed_pattern
FROM
(
SELECT '%' & T1.line_feed & '%'
& T2.line_feed & '%' & T3.line_feed & '%'
& T4.line_feed & '%' & T5.line_feed & '%'
AS line_feed_pattern
FROM LineFeeds AS T1,
LineFeeds AS T2, LineFeeds AS T3,
LineFeeds AS T4, LineFeeds AS T5
UNION ALL
SELECT '*' & T1.line_feed & '*'
& T2.line_feed & '*' & T3.line_feed & '*'
& T4.line_feed & '*' & T5.line_feed & '*'
AS line_feed_pattern
FROM LineFeeds AS T1,
LineFeeds AS T2, LineFeeds AS T3,
LineFeeds AS T4, LineFeeds AS T5
) AS DT1
;
Now the CHECK constraint (validation rule) is simply a matter of using
a LIKE join:
CREATE TABLE Test1 (
memo_col MEMO NOT NULL,
CONSTRAINT memo_col__max_five_lines
CHECK (
0 = (
SELECT COUNT(*)
FROM Test1 AS T1,
LineFeedPatterns AS L1
WHERE T1.memo_col LIKE L1.line_feed_pattern
)
)
)
;
As ever, here's the VBA code to reproduce and test the above SQL:
Sub linefeeds()
Dim cat
Set cat = CreateObject("ADOX.Catalog")
With cat
.Create _
"Provider=Microsoft.Jet.OLEDB.4.0;" & _
"Data Source=C:\DropMe.mdb"
With .ActiveConnection
' Create all possible line feeds (4)
.Execute _
"CREATE TABLE LineFeeds (line_feed VARCHAR(2)" & _
" NOT NULL UNIQUE);"
.Execute _
"INSERT INTO LineFeeds (line_feed) VALUES" & _
" (CHR$(10) & CHR$(13));"
.Execute _
"INSERT INTO LineFeeds (line_feed) VALUES" & _
" (CHR$(13) & CHR$(10));"
.Execute _
"INSERT INTO LineFeeds (line_feed) VALUES" & _
" (CHR$(13));"
.Execute _
"INSERT INTO LineFeeds (line_feed) VALUES" & _
" (CHR$(10));"
' Create all possible line feeds and combinations
' for each flavour of wildcard character (2048)
.Execute _
"CREATE TABLE LineFeedPatterns (line_feed_pattern" & _
" VARCHAR(143) NOT NULL UNIQUE);"
.Execute _
"INSERT INTO LineFeedPatterns (line_feed_pattern)" & _
" SELECT DT1.line_feed_pattern FROM ( SELECT" & _
" '%' & T1.line_feed & '%' & T2.line_feed" & _
" & '%' & T3.line_feed & '%' & T4.line_feed" & _
" & '%' & T5.line_feed & '%' AS line_feed_pattern" & _
" FROM LineFeeds AS T1, LineFeeds AS T2," & _
" LineFeeds AS T3, LineFeeds AS T4, LineFeeds" & _
" AS T5 UNION ALL SELECT '*' & T1.line_feed" & _
" & '*' & T2.line_feed & '*' & T3.line_feed" & _
" & '*' & T4.line_feed & '*' & T5.line_feed" & _
" & '*' AS line_feed_pattern FROM LineFeeds" & _
" AS T1, LineFeeds AS T2, LineFeeds AS T3," & _
" LineFeeds AS T4, LineFeeds AS T5 ) AS DT1;"
' Create test table with CHECK constraint
.Execute _
"CREATE TABLE Test1 ( memo_col MEMO NOT NULL," & _
" CONSTRAINT memo_col__max_five_lines CHECK" & _
" ( 0 = ( SELECT COUNT(*) FROM Test1 AS T1," & _
" LineFeedPatterns AS L1 WHERE T1.memo_col" & _
" LIKE L1.line_feed_pattern )));"
' This (five lines) will succeed
.Execute _
"INSERT INTO Test1 (memo_col) VALUES ('legal'" & _
" & CHR$(10) & 'legal' & CHR$(10) & 'legal'" & _
" & CHR$(10) & 'legal' & CHR$(10) & 'legal');"
' This (six lines) will fail
.Execute _
"INSERT INTO Test1 (memo_col) VALUES ('illegal'" & _
" & CHR$(10) & 'illegal' & CHR$(10) & 'illegal'" & _
" & CHR$(10) & 'illegal' & CHR$(10) & 'illegal'" & _
" & CHR$(10) & 'illegal');"
End With
Set .ActiveConnection = Nothing
End With
End Sub
Jamie.
--