Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
mariadb
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
mariadb
Commits
4cfb6d97
Commit
4cfb6d97
authored
Dec 19, 2002
by
bell@sanja.is.com.ua
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
support of simple row subselects (SCRUM)
parent
b785e980
Changes
8
Hide whitespace changes
Inline
Side-by-side
Showing
8 changed files
with
307 additions
and
69 deletions
+307
-69
mysql-test/r/subselect.result
mysql-test/r/subselect.result
+69
-1
mysql-test/t/subselect.test
mysql-test/t/subselect.test
+26
-1
sql/item.cc
sql/item.cc
+54
-0
sql/item.h
sql/item.h
+7
-19
sql/item_cmpfunc.cc
sql/item_cmpfunc.cc
+7
-0
sql/item_subselect.cc
sql/item_subselect.cc
+129
-40
sql/item_subselect.h
sql/item_subselect.h
+12
-6
sql/sql_class.cc
sql/sql_class.cc
+3
-2
No files found.
mysql-test/r/subselect.result
View file @
4cfb6d97
...
@@ -52,6 +52,54 @@ a
...
@@ -52,6 +52,54 @@ a
SELECT (SELECT 1) as a FROM (SELECT 1) b WHERE (SELECT a) IS NOT NULL;
SELECT (SELECT 1) as a FROM (SELECT 1) b WHERE (SELECT a) IS NOT NULL;
a
a
1
1
SELECT (SELECT 1,2,3) = ROW(1,2,3);
(SELECT 1,2,3) = ROW(1,2,3)
1
SELECT (SELECT 1,2,3) = ROW(1,2,1);
(SELECT 1,2,3) = ROW(1,2,1)
0
SELECT (SELECT 1,2,3) < ROW(1,2,1);
(SELECT 1,2,3) < ROW(1,2,1)
0
SELECT (SELECT 1,2,3) > ROW(1,2,1);
(SELECT 1,2,3) > ROW(1,2,1)
1
SELECT (SELECT 1,2,3) = ROW(1,2,NULL);
(SELECT 1,2,3) = ROW(1,2,NULL)
NULL
SELECT ROW(1,2,3) = (SELECT 1,2,3);
ROW(1,2,3) = (SELECT 1,2,3)
1
SELECT ROW(1,2,3) = (SELECT 1,2,1);
ROW(1,2,3) = (SELECT 1,2,1)
0
SELECT ROW(1,2,3) < (SELECT 1,2,1);
ROW(1,2,3) < (SELECT 1,2,1)
0
SELECT ROW(1,2,3) > (SELECT 1,2,1);
ROW(1,2,3) > (SELECT 1,2,1)
1
SELECT ROW(1,2,3) = (SELECT 1,2,NULL);
ROW(1,2,3) = (SELECT 1,2,NULL)
NULL
SELECT (SELECT 1.5,2,'a') = ROW(1.5,2,'a');
(SELECT 1.5,2,'a') = ROW(1.5,2,'a')
1
SELECT (SELECT 1.5,2,'a') = ROW(1.5,2,'b');
(SELECT 1.5,2,'a') = ROW(1.5,2,'b')
0
SELECT (SELECT 1.5,2,'a') = ROW('b',2,'b');
(SELECT 1.5,2,'a') = ROW('b',2,'b')
0
SELECT (SELECT 'b',2,'a') = ROW(1.5,2,'a');
(SELECT 'b',2,'a') = ROW(1.5,2,'a')
0
SELECT (SELECT 1.5,2,'a') = ROW(1.5,'c','a');
(SELECT 1.5,2,'a') = ROW(1.5,'c','a')
0
SELECT (SELECT 1.5,'c','a') = ROW(1.5,2,'a');
(SELECT 1.5,'c','a') = ROW(1.5,2,'a')
0
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8;
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8;
create table t1 (a int);
create table t1 (a int);
create table t2 (a int, b int);
create table t2 (a int, b int);
...
@@ -602,7 +650,7 @@ CREATE TABLE t1 (id int(11) default NULL, KEY id (id)) TYPE=MyISAM CHARSET=latin
...
@@ -602,7 +650,7 @@ CREATE TABLE t1 (id int(11) default NULL, KEY id (id)) TYPE=MyISAM CHARSET=latin
INSERT INTO t1 values (1),(1);
INSERT INTO t1 values (1),(1);
UPDATE t SET id=(SELECT * FROM t1);
UPDATE t SET id=(SELECT * FROM t1);
Subselect returns more than 1 record
Subselect returns more than 1 record
drop table t;
drop table t
, t1
;
create table t (a int);
create table t (a int);
insert into t values (1),(2),(3);
insert into t values (1),(2),(3);
select 1 IN (SELECT * from t);
select 1 IN (SELECT * from t);
...
@@ -705,3 +753,23 @@ select 10.5 > ANY (SELECT * from t);
...
@@ -705,3 +753,23 @@ select 10.5 > ANY (SELECT * from t);
10.5 > ANY (SELECT * from t)
10.5 > ANY (SELECT * from t)
1
1
drop table t;
drop table t;
create table t1 (a int, b int, c varchar(10));
create table t2 (a int);
insert into t1 values (1,2,'a'),(2,3,'b'),(3,4,'c');
insert into t2 values (1),(2),(NULL);
select a, (select a,b,c from t1 where t1.a=t2.a) = ROW(a,2,'a'),(select c from t1 where a=t2.a) from t2;
a (select a,b,c from t1 where t1.a=t2.a) = ROW(a,2,'a') (select c from t1 where a=t2.a)
1 1 a
2 0 b
NULL NULL NULL
select a, (select a,b,c from t1 where t1.a=t2.a) = ROW(a,3,'b'),(select c from t1 where a=t2.a) from t2;
a (select a,b,c from t1 where t1.a=t2.a) = ROW(a,3,'b') (select c from t1 where a=t2.a)
1 0 a
2 1 b
NULL NULL NULL
select a, (select a,b,c from t1 where t1.a=t2.a) = ROW(a,4,'c'),(select c from t1 where a=t2.a) from t2;
a (select a,b,c from t1 where t1.a=t2.a) = ROW(a,4,'c') (select c from t1 where a=t2.a)
1 0 a
2 0 b
NULL NULL NULL
drop table t1,t2;
mysql-test/t/subselect.test
View file @
4cfb6d97
...
@@ -26,6 +26,22 @@ select (SELECT 1 FROM (SELECT 1) a PROCEDURE ANALYSE(1));
...
@@ -26,6 +26,22 @@ select (SELECT 1 FROM (SELECT 1) a PROCEDURE ANALYSE(1));
SELECT
1
FROM
(
SELECT
1
)
a
PROCEDURE
ANALYSE
((
SELECT
1
));
SELECT
1
FROM
(
SELECT
1
)
a
PROCEDURE
ANALYSE
((
SELECT
1
));
SELECT
(
SELECT
1
)
as
a
FROM
(
SELECT
1
)
b
WHERE
(
SELECT
a
)
IS
NULL
;
SELECT
(
SELECT
1
)
as
a
FROM
(
SELECT
1
)
b
WHERE
(
SELECT
a
)
IS
NULL
;
SELECT
(
SELECT
1
)
as
a
FROM
(
SELECT
1
)
b
WHERE
(
SELECT
a
)
IS
NOT
NULL
;
SELECT
(
SELECT
1
)
as
a
FROM
(
SELECT
1
)
b
WHERE
(
SELECT
a
)
IS
NOT
NULL
;
SELECT
(
SELECT
1
,
2
,
3
)
=
ROW
(
1
,
2
,
3
);
SELECT
(
SELECT
1
,
2
,
3
)
=
ROW
(
1
,
2
,
1
);
SELECT
(
SELECT
1
,
2
,
3
)
<
ROW
(
1
,
2
,
1
);
SELECT
(
SELECT
1
,
2
,
3
)
>
ROW
(
1
,
2
,
1
);
SELECT
(
SELECT
1
,
2
,
3
)
=
ROW
(
1
,
2
,
NULL
);
SELECT
ROW
(
1
,
2
,
3
)
=
(
SELECT
1
,
2
,
3
);
SELECT
ROW
(
1
,
2
,
3
)
=
(
SELECT
1
,
2
,
1
);
SELECT
ROW
(
1
,
2
,
3
)
<
(
SELECT
1
,
2
,
1
);
SELECT
ROW
(
1
,
2
,
3
)
>
(
SELECT
1
,
2
,
1
);
SELECT
ROW
(
1
,
2
,
3
)
=
(
SELECT
1
,
2
,
NULL
);
SELECT
(
SELECT
1.5
,
2
,
'a'
)
=
ROW
(
1.5
,
2
,
'a'
);
SELECT
(
SELECT
1.5
,
2
,
'a'
)
=
ROW
(
1.5
,
2
,
'b'
);
SELECT
(
SELECT
1.5
,
2
,
'a'
)
=
ROW
(
'b'
,
2
,
'b'
);
SELECT
(
SELECT
'b'
,
2
,
'a'
)
=
ROW
(
1.5
,
2
,
'a'
);
SELECT
(
SELECT
1.5
,
2
,
'a'
)
=
ROW
(
1.5
,
'c'
,
'a'
);
SELECT
(
SELECT
1.5
,
'c'
,
'a'
)
=
ROW
(
1.5
,
2
,
'a'
);
drop
table
if
exists
t1
,
t2
,
t3
,
t4
,
t5
,
t6
,
t7
,
t8
;
drop
table
if
exists
t1
,
t2
,
t3
,
t4
,
t5
,
t6
,
t7
,
t8
;
create
table
t1
(
a
int
);
create
table
t1
(
a
int
);
...
@@ -363,7 +379,7 @@ CREATE TABLE t1 (id int(11) default NULL, KEY id (id)) TYPE=MyISAM CHARSET=latin
...
@@ -363,7 +379,7 @@ CREATE TABLE t1 (id int(11) default NULL, KEY id (id)) TYPE=MyISAM CHARSET=latin
INSERT
INTO
t1
values
(
1
),(
1
);
INSERT
INTO
t1
values
(
1
),(
1
);
--
error
1240
--
error
1240
UPDATE
t
SET
id
=
(
SELECT
*
FROM
t1
);
UPDATE
t
SET
id
=
(
SELECT
*
FROM
t1
);
drop
table
t
;
drop
table
t
,
t1
;
#NULL test
#NULL test
...
@@ -409,3 +425,12 @@ select 10.5 > ALL (SELECT * from t);
...
@@ -409,3 +425,12 @@ select 10.5 > ALL (SELECT * from t);
select
1.5
>
ANY
(
SELECT
*
from
t
);
select
1.5
>
ANY
(
SELECT
*
from
t
);
select
10.5
>
ANY
(
SELECT
*
from
t
);
select
10.5
>
ANY
(
SELECT
*
from
t
);
drop
table
t
;
drop
table
t
;
create
table
t1
(
a
int
,
b
int
,
c
varchar
(
10
));
create
table
t2
(
a
int
);
insert
into
t1
values
(
1
,
2
,
'a'
),(
2
,
3
,
'b'
),(
3
,
4
,
'c'
);
insert
into
t2
values
(
1
),(
2
),(
NULL
);
select
a
,
(
select
a
,
b
,
c
from
t1
where
t1
.
a
=
t2
.
a
)
=
ROW
(
a
,
2
,
'a'
),(
select
c
from
t1
where
a
=
t2
.
a
)
from
t2
;
select
a
,
(
select
a
,
b
,
c
from
t1
where
t1
.
a
=
t2
.
a
)
=
ROW
(
a
,
3
,
'b'
),(
select
c
from
t1
where
a
=
t2
.
a
)
from
t2
;
select
a
,
(
select
a
,
b
,
c
from
t1
where
t1
.
a
=
t2
.
a
)
=
ROW
(
a
,
4
,
'c'
),(
select
c
from
t1
where
a
=
t2
.
a
)
from
t2
;
drop
table
t1
,
t2
;
sql/item.cc
View file @
4cfb6d97
...
@@ -1217,6 +1217,60 @@ bool field_is_equal_to_item(Field *field,Item *item)
...
@@ -1217,6 +1217,60 @@ bool field_is_equal_to_item(Field *field,Item *item)
return
result
==
field
->
val_real
();
return
result
==
field
->
val_real
();
}
}
Item_cache
*
Item_cache
::
get_cache
(
Item_result
type
)
{
switch
(
type
)
{
case
INT_RESULT
:
return
new
Item_cache_int
();
case
REAL_RESULT
:
return
new
Item_cache_real
();
case
STRING_RESULT
:
return
new
Item_cache_str
();
default:
// should never be in real life
DBUG_ASSERT
(
0
);
return
0
;
}
}
void
Item_cache_str
::
store
(
Item
*
item
)
{
str_value
.
set
(
buffer
,
sizeof
(
buffer
),
item
->
charset
());
value
=
item
->
str_result
(
&
str_value
);
if
((
null_value
=
item
->
null_value
))
value
=
0
;
else
if
(
value
!=
&
str_value
)
{
/*
We copy string value to avoid changing value if 'item' is table field
in queries like following (where t1.c is varchar):
select a,
(select a,b,c from t1 where t1.a=t2.a) = ROW(a,2,'a'),
(select c from t1 where a=t2.a)
from t2;
*/
str_value
.
copy
(
*
value
);
value
=
&
str_value
;
}
}
double
Item_cache_str
::
val
()
{
if
(
value
)
return
my_strntod
(
value
->
charset
(),
value
->
ptr
(),
value
->
length
(),
(
char
**
)
0
);
else
return
(
double
)
0
;
}
longlong
Item_cache_str
::
val_int
()
{
if
(
value
)
return
my_strntoll
(
value
->
charset
(),
value
->
ptr
(),
value
->
length
(),
(
char
**
)
0
,
10
);
else
return
(
longlong
)
0
;
}
/*****************************************************************************
/*****************************************************************************
** Instantiate templates
** Instantiate templates
...
...
sql/item.h
View file @
4cfb6d97
...
@@ -103,7 +103,9 @@ public:
...
@@ -103,7 +103,9 @@ public:
virtual
Item
**
addr
(
uint
i
)
{
return
0
;
}
virtual
Item
**
addr
(
uint
i
)
{
return
0
;
}
virtual
bool
check_cols
(
uint
c
);
virtual
bool
check_cols
(
uint
c
);
// It is not row => null inside is impossible
// It is not row => null inside is impossible
virtual
bool
null_inside
()
{
return
0
;
};
virtual
bool
null_inside
()
{
return
0
;
}
// used in row subselects to get value of elements
virtual
void
bring_value
()
{}
};
};
...
@@ -719,6 +721,7 @@ public:
...
@@ -719,6 +721,7 @@ public:
decimals
=
dec
;
decimals
=
dec
;
}
}
enum
Type
type
()
const
{
return
CACHE_ITEM
;
}
enum
Type
type
()
const
{
return
CACHE_ITEM
;
}
static
Item_cache
*
get_cache
(
Item_result
type
);
};
};
class
Item_cache_int
:
public
Item_cache
class
Item_cache_int
:
public
Item_cache
...
@@ -766,24 +769,9 @@ class Item_cache_str: public Item_cache
...
@@ -766,24 +769,9 @@ class Item_cache_str: public Item_cache
public:
public:
Item_cache_str
()
{
fixed
=
1
;
null_value
=
1
;
}
Item_cache_str
()
{
fixed
=
1
;
null_value
=
1
;
}
void
store
(
Item
*
item
)
void
store
(
Item
*
item
);
{
double
val
();
str_value
.
set
(
buffer
,
sizeof
(
buffer
),
item
->
charset
());
longlong
val_int
();
value
=
item
->
str_result
(
&
str_value
);
// TODO remove if str_value charset have no side effect for now
str_value
.
set_charset
(
value
->
charset
());
null_value
=
item
->
null_value
;
}
double
val
()
{
return
my_strntod
(
value
->
charset
(),
value
->
ptr
(),
value
->
length
(),
(
char
**
)
0
);
}
longlong
val_int
()
{
return
my_strntoll
(
value
->
charset
(),
value
->
ptr
(),
value
->
length
(),
(
char
**
)
0
,
10
);
}
String
*
val_str
(
String
*
)
{
return
value
;
}
String
*
val_str
(
String
*
)
{
return
value
;
}
enum
Item_result
result_type
()
const
{
return
STRING_RESULT
;
}
enum
Item_result
result_type
()
const
{
return
STRING_RESULT
;
}
CHARSET_INFO
*
charset
()
const
{
return
value
->
charset
();
};
CHARSET_INFO
*
charset
()
const
{
return
value
->
charset
();
};
...
...
sql/item_cmpfunc.cc
View file @
4cfb6d97
...
@@ -247,6 +247,8 @@ int Arg_comparator::compare_e_int()
...
@@ -247,6 +247,8 @@ int Arg_comparator::compare_e_int()
int
Arg_comparator
::
compare_row
()
int
Arg_comparator
::
compare_row
()
{
{
int
res
=
0
;
int
res
=
0
;
(
*
a
)
->
bring_value
();
(
*
b
)
->
bring_value
();
uint
n
=
(
*
a
)
->
cols
();
uint
n
=
(
*
a
)
->
cols
();
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
{
{
...
@@ -261,6 +263,8 @@ int Arg_comparator::compare_row()
...
@@ -261,6 +263,8 @@ int Arg_comparator::compare_row()
int
Arg_comparator
::
compare_e_row
()
int
Arg_comparator
::
compare_e_row
()
{
{
int
res
=
0
;
int
res
=
0
;
(
*
a
)
->
bring_value
();
(
*
b
)
->
bring_value
();
uint
n
=
(
*
a
)
->
cols
();
uint
n
=
(
*
a
)
->
cols
();
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
{
{
...
@@ -1219,6 +1223,7 @@ void cmp_item_row::store_value(Item *item)
...
@@ -1219,6 +1223,7 @@ void cmp_item_row::store_value(Item *item)
n
=
item
->
cols
();
n
=
item
->
cols
();
if
((
comparators
=
(
cmp_item
**
)
thd
->
alloc
(
sizeof
(
cmp_item
*
)
*
n
)))
if
((
comparators
=
(
cmp_item
**
)
thd
->
alloc
(
sizeof
(
cmp_item
*
)
*
n
)))
{
{
item
->
bring_value
();
item
->
null_value
=
0
;
item
->
null_value
=
0
;
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
if
((
comparators
[
i
]
=
cmp_item
::
get_comparator
(
item
->
el
(
i
))))
if
((
comparators
[
i
]
=
cmp_item
::
get_comparator
(
item
->
el
(
i
))))
...
@@ -1252,6 +1257,7 @@ void cmp_item_row::store_value_by_template(cmp_item *t, Item *item)
...
@@ -1252,6 +1257,7 @@ void cmp_item_row::store_value_by_template(cmp_item *t, Item *item)
n
=
tmpl
->
n
;
n
=
tmpl
->
n
;
if
((
comparators
=
(
cmp_item
**
)
sql_alloc
(
sizeof
(
cmp_item
*
)
*
n
)))
if
((
comparators
=
(
cmp_item
**
)
sql_alloc
(
sizeof
(
cmp_item
*
)
*
n
)))
{
{
item
->
bring_value
();
item
->
null_value
=
0
;
item
->
null_value
=
0
;
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
if
((
comparators
[
i
]
=
tmpl
->
comparators
[
i
]
->
make_same
()))
if
((
comparators
[
i
]
=
tmpl
->
comparators
[
i
]
->
make_same
()))
...
@@ -1284,6 +1290,7 @@ int cmp_item_row::cmp(Item *arg)
...
@@ -1284,6 +1290,7 @@ int cmp_item_row::cmp(Item *arg)
return
1
;
return
1
;
}
}
bool
was_null
=
0
;
bool
was_null
=
0
;
arg
->
bring_value
();
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
for
(
uint
i
=
0
;
i
<
n
;
i
++
)
if
(
comparators
[
i
]
->
cmp
(
arg
->
el
(
i
)))
if
(
comparators
[
i
]
->
cmp
(
arg
->
el
(
i
)))
{
{
...
...
sql/item_subselect.cc
View file @
4cfb6d97
...
@@ -112,9 +112,14 @@ bool Item_subselect::check_loop(uint id)
...
@@ -112,9 +112,14 @@ bool Item_subselect::check_loop(uint id)
DBUG_RETURN
(
engine
->
check_loop
(
id
));
DBUG_RETURN
(
engine
->
check_loop
(
id
));
}
}
Item
::
Type
Item_subselect
::
type
()
const
{
return
SUBSELECT_ITEM
;
}
void
Item_subselect
::
fix_length_and_dec
()
void
Item_subselect
::
fix_length_and_dec
()
{
{
engine
->
fix_length_and_dec
();
engine
->
fix_length_and_dec
(
0
);
}
}
inline
table_map
Item_subselect
::
used_tables
()
const
inline
table_map
Item_subselect
::
used_tables
()
const
...
@@ -130,6 +135,7 @@ Item_singleval_subselect::Item_singleval_subselect(THD *thd,
...
@@ -130,6 +135,7 @@ Item_singleval_subselect::Item_singleval_subselect(THD *thd,
init
(
thd
,
select_lex
,
new
select_singleval_subselect
(
this
));
init
(
thd
,
select_lex
,
new
select_singleval_subselect
(
this
));
max_columns
=
1
;
max_columns
=
1
;
maybe_null
=
1
;
maybe_null
=
1
;
max_columns
=
UINT_MAX
;
DBUG_VOID_RETURN
;
DBUG_VOID_RETURN
;
}
}
...
@@ -140,9 +146,9 @@ void Item_singleval_subselect::reset()
...
@@ -140,9 +146,9 @@ void Item_singleval_subselect::reset()
value
->
null_value
=
1
;
value
->
null_value
=
1
;
}
}
void
Item_singleval_subselect
::
store
(
Item
*
item
)
void
Item_singleval_subselect
::
store
(
uint
i
,
Item
*
item
)
{
{
value
->
store
(
item
);
row
[
i
]
->
store
(
item
);
}
}
enum
Item_result
Item_singleval_subselect
::
result_type
()
const
enum
Item_result
Item_singleval_subselect
::
result_type
()
const
...
@@ -152,29 +158,58 @@ enum Item_result Item_singleval_subselect::result_type() const
...
@@ -152,29 +158,58 @@ enum Item_result Item_singleval_subselect::result_type() const
void
Item_singleval_subselect
::
fix_length_and_dec
()
void
Item_singleval_subselect
::
fix_length_and_dec
()
{
{
engine
->
fix_length_and_dec
();
if
((
max_columns
=
engine
->
cols
())
==
1
)
switch
(
engine
->
type
())
{
engine
->
fix_length_and_dec
(
row
=
&
value
);
if
(
!
(
value
=
Item_cache
::
get_cache
(
engine
->
type
())))
{
my_message
(
ER_OUT_OF_RESOURCES
,
ER
(
ER_OUT_OF_RESOURCES
),
MYF
(
0
));
current_thd
->
fatal_error
=
1
;
return
;
}
}
else
{
{
case
INT_RESULT
:
THD
*
thd
=
current_thd
;
value
=
new
Item_cache_int
();
if
(
!
(
row
=
(
Item_cache
**
)
thd
->
alloc
(
sizeof
(
Item_cache
*
)
*
max_columns
)))
break
;
{
case
REAL_RESULT
:
my_message
(
ER_OUT_OF_RESOURCES
,
ER
(
ER_OUT_OF_RESOURCES
),
MYF
(
0
));
value
=
new
Item_cache_real
();
thd
->
fatal_error
=
1
;
break
;
return
;
case
STRING_RESULT
:
}
value
=
new
Item_cache_str
();
engine
->
fix_length_and_dec
(
row
);
break
;
value
=
*
row
;
default:
// should never be in real life
DBUG_ASSERT
(
0
);
return
;
}
}
value
->
set_len_n_dec
(
max_length
,
decimals
);
}
}
Item
::
Type
Item_subselect
::
type
()
const
uint
Item_singleval_subselect
::
cols
()
{
{
return
SUBSELECT_ITEM
;
return
engine
->
cols
();
}
bool
Item_singleval_subselect
::
check_cols
(
uint
c
)
{
if
(
c
!=
engine
->
cols
())
{
my_error
(
ER_CARDINALITY_COL
,
MYF
(
0
),
c
);
return
1
;
}
return
0
;
}
bool
Item_singleval_subselect
::
null_inside
()
{
for
(
uint
i
=
0
;
i
<
max_columns
;
i
++
)
{
if
(
row
[
i
]
->
null_value
)
return
1
;
}
return
0
;
}
void
Item_singleval_subselect
::
bring_value
()
{
engine
->
exec
();
}
}
double
Item_singleval_subselect
::
val
()
double
Item_singleval_subselect
::
val
()
...
@@ -268,7 +303,7 @@ Item_allany_subselect::Item_allany_subselect(THD *thd, Item * left_exp,
...
@@ -268,7 +303,7 @@ Item_allany_subselect::Item_allany_subselect(THD *thd, Item * left_exp,
void
Item_exists_subselect
::
fix_length_and_dec
()
void
Item_exists_subselect
::
fix_length_and_dec
()
{
{
decimals
=
0
;
decimals
=
0
;
max_length
=
1
;
max_length
=
1
;
}
}
...
@@ -540,31 +575,85 @@ int subselect_union_engine::prepare()
...
@@ -540,31 +575,85 @@ int subselect_union_engine::prepare()
return
unit
->
prepare
(
thd
,
result
);
return
unit
->
prepare
(
thd
,
result
);
}
}
void
subselect_single_select_engine
::
fix_length_and_dec
()
static
Item_result
set_row
(
SELECT_LEX
*
select_lex
,
Item
*
item
,
Item_cache
**
row
)
{
{
Item_result
res_type
=
STRING_RESULT
;
Item
*
sel_item
;
List_iterator_fast
<
Item
>
li
(
select_lex
->
item_list
);
List_iterator_fast
<
Item
>
li
(
select_lex
->
item_list
);
Item
*
sel_item
=
li
++
;
for
(
uint
i
=
0
;
(
sel_item
=
li
++
);
i
++
)
item
->
max_length
=
sel_item
->
max_length
;
{
res_type
=
sel_item
->
result_type
();
item
->
max_length
=
sel_item
->
max_length
;
item
->
decimals
=
sel_item
->
decimals
;
res_type
=
sel_item
->
result_type
();
item
->
decimals
=
sel_item
->
decimals
;
if
(
row
)
{
if
(
!
(
row
[
i
]
=
Item_cache
::
get_cache
(
res_type
)))
{
my_message
(
ER_OUT_OF_RESOURCES
,
ER
(
ER_OUT_OF_RESOURCES
),
MYF
(
0
));
current_thd
->
fatal_error
=
1
;
return
STRING_RESULT
;
// we should return something
}
row
[
i
]
->
set_len_n_dec
(
sel_item
->
max_length
,
sel_item
->
decimals
);
}
}
if
(
select_lex
->
item_list
.
elements
>
1
)
res_type
=
ROW_RESULT
;
return
res_type
;
}
}
void
subselect_
union_engine
::
fix_length_and_dec
(
)
void
subselect_
single_select_engine
::
fix_length_and_dec
(
Item_cache
**
row
)
{
{
uint32
mlen
=
0
,
len
;
DBUG_ASSERT
(
row
||
select_lex
->
item_list
.
elements
==
1
);
Item
*
sel_item
=
0
;
res_type
=
set_row
(
select_lex
,
item
,
row
);
for
(
SELECT_LEX
*
sl
=
unit
->
first_select
();
sl
;
sl
=
sl
->
next_select
())
}
void
subselect_union_engine
::
fix_length_and_dec
(
Item_cache
**
row
)
{
DBUG_ASSERT
(
row
||
unit
->
first_select
()
->
item_list
.
elements
==
1
);
if
(
unit
->
first_select
()
->
item_list
.
elements
==
1
)
{
{
List_iterator_fast
<
Item
>
li
(
sl
->
item_list
);
uint32
mlen
=
0
,
len
;
Item
*
s_item
=
li
++
;
Item
*
sel_item
=
0
;
if
((
len
=
s_item
->
max_length
))
for
(
SELECT_LEX
*
sl
=
unit
->
first_select
();
sl
;
sl
=
sl
->
next_select
())
mlen
=
len
;
{
if
(
!
sel_item
)
List_iterator_fast
<
Item
>
li
(
sl
->
item_list
);
sel_item
=
s_item
;
Item
*
s_item
=
li
++
;
if
((
len
=
s_item
->
max_length
)
>
mlen
)
mlen
=
len
;
if
(
!
sel_item
)
sel_item
=
s_item
;
}
item
->
max_length
=
mlen
;
res_type
=
sel_item
->
result_type
();
item
->
decimals
=
sel_item
->
decimals
;
if
(
row
)
{
if
(
!
(
row
[
0
]
=
Item_cache
::
get_cache
(
res_type
)))
{
my_message
(
ER_OUT_OF_RESOURCES
,
ER
(
ER_OUT_OF_RESOURCES
),
MYF
(
0
));
current_thd
->
fatal_error
=
1
;
return
;
}
row
[
0
]
->
set_len_n_dec
(
mlen
,
sel_item
->
decimals
);
}
}
else
{
SELECT_LEX
*
sl
=
unit
->
first_select
();
res_type
=
set_row
(
sl
,
item
,
row
);
for
(
sl
=
sl
->
next_select
();
sl
;
sl
->
next_select
())
{
List_iterator_fast
<
Item
>
li
(
sl
->
item_list
);
Item
*
sel_item
;
for
(
uint
i
=
0
;
(
sel_item
=
li
++
);
i
++
)
{
if
(
sel_item
->
max_length
>
row
[
i
]
->
max_length
)
row
[
i
]
->
max_length
=
sel_item
->
max_length
;
}
}
}
}
item
->
max_length
=
mlen
;
res_type
=
sel_item
->
result_type
();
item
->
decimals
=
sel_item
->
decimals
;
}
}
int
subselect_single_select_engine
::
exec
()
int
subselect_single_select_engine
::
exec
()
...
...
sql/item_subselect.h
View file @
4cfb6d97
...
@@ -94,8 +94,7 @@ class Item_cache;
...
@@ -94,8 +94,7 @@ class Item_cache;
class
Item_singleval_subselect
:
public
Item_subselect
class
Item_singleval_subselect
:
public
Item_subselect
{
{
protected:
protected:
Item_cache
*
value
;
Item_cache
*
value
,
**
row
;
public:
public:
Item_singleval_subselect
(
THD
*
thd
,
st_select_lex
*
select_lex
);
Item_singleval_subselect
(
THD
*
thd
,
st_select_lex
*
select_lex
);
Item_singleval_subselect
(
Item_singleval_subselect
*
item
)
:
Item_singleval_subselect
(
Item_singleval_subselect
*
item
)
:
...
@@ -106,7 +105,7 @@ public:
...
@@ -106,7 +105,7 @@ public:
decimals
=
item
->
decimals
;
decimals
=
item
->
decimals
;
}
}
void
reset
();
void
reset
();
void
store
(
Item
*
item
);
void
store
(
uint
i
,
Item
*
item
);
double
val
();
double
val
();
longlong
val_int
();
longlong
val_int
();
String
*
val_str
(
String
*
);
String
*
val_str
(
String
*
);
...
@@ -114,6 +113,13 @@ public:
...
@@ -114,6 +113,13 @@ public:
enum
Item_result
result_type
()
const
;
enum
Item_result
result_type
()
const
;
void
fix_length_and_dec
();
void
fix_length_and_dec
();
uint
cols
();
Item
*
el
(
uint
i
)
{
return
(
Item
*
)
row
[
i
];
}
Item
**
addr
(
uint
i
)
{
return
(
Item
**
)
row
+
i
;
}
bool
check_cols
(
uint
c
);
bool
null_inside
();
void
bring_value
();
friend
class
select_singleval_subselect
;
friend
class
select_singleval_subselect
;
};
};
...
@@ -212,7 +218,7 @@ public:
...
@@ -212,7 +218,7 @@ public:
}
}
virtual
int
prepare
()
=
0
;
virtual
int
prepare
()
=
0
;
virtual
void
fix_length_and_dec
()
=
0
;
virtual
void
fix_length_and_dec
(
Item_cache
**
row
)
=
0
;
virtual
int
exec
()
=
0
;
virtual
int
exec
()
=
0
;
virtual
uint
cols
()
=
0
;
/* return number of columnss in select */
virtual
uint
cols
()
=
0
;
/* return number of columnss in select */
virtual
bool
depended
()
=
0
;
/* depended from outer select */
virtual
bool
depended
()
=
0
;
/* depended from outer select */
...
@@ -233,7 +239,7 @@ public:
...
@@ -233,7 +239,7 @@ public:
select_subselect
*
result
,
select_subselect
*
result
,
Item_subselect
*
item
);
Item_subselect
*
item
);
int
prepare
();
int
prepare
();
void
fix_length_and_dec
();
void
fix_length_and_dec
(
Item_cache
**
row
);
int
exec
();
int
exec
();
uint
cols
();
uint
cols
();
bool
depended
();
bool
depended
();
...
@@ -250,7 +256,7 @@ public:
...
@@ -250,7 +256,7 @@ public:
select_subselect
*
result
,
select_subselect
*
result
,
Item_subselect
*
item
);
Item_subselect
*
item
);
int
prepare
();
int
prepare
();
void
fix_length_and_dec
();
void
fix_length_and_dec
(
Item_cache
**
row
);
int
exec
();
int
exec
();
uint
cols
();
uint
cols
();
bool
depended
();
bool
depended
();
...
...
sql/sql_class.cc
View file @
4cfb6d97
...
@@ -931,8 +931,9 @@ bool select_singleval_subselect::send_data(List<Item> &items)
...
@@ -931,8 +931,9 @@ bool select_singleval_subselect::send_data(List<Item> &items)
DBUG_RETURN
(
0
);
DBUG_RETURN
(
0
);
}
}
List_iterator_fast
<
Item
>
li
(
items
);
List_iterator_fast
<
Item
>
li
(
items
);
Item
*
val_item
=
li
++
;
// Only one (single value subselect)
Item
*
val_item
;
it
->
store
(
val_item
);
for
(
uint
i
=
0
;
(
val_item
=
li
++
);
i
++
)
it
->
store
(
i
,
val_item
);
it
->
assigned
(
1
);
it
->
assigned
(
1
);
DBUG_RETURN
(
0
);
DBUG_RETURN
(
0
);
}
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment