我在java代码里面 编写了如下sql语句!
public class StorageDaoImpl extends BaseDao implements StorageDao {
private Connection con=null;
private PreparedStatement pstmt=null;
private ResultSet rs=null;
private String sql=null;
private String[] str={"name","price","number","makeTime","电器","食品","服装","日用品"};
private List<StorageBean> list=new ArrayList<StorageBean>();
private StorageBean sBean=null; public List<StorageBean> getStorage(int id) throws Exception {
con=this.getConnection();
if(id<5){
//sql语句是我如此构建的 如果直接sql="select * from storage order by name";运行能成功,
//但是下面这样就不可以?这是为什么?
sql="select * from storage order by ?";
pstmt=con.prepareStatement(sql);
pstmt.setString(1, str[id-1]);
}else {
sql="select * from storage where type like ?";
pstmt=con.prepareStatement(sql);
pstmt.setString(1, str[id-1]);
}
rs=pstmt.executeQuery();
while(rs.next()){
sBean=new StorageBean();
sBean.setId(rs.getInt(1));
sBean.setName(rs.getString(2));
sBean.setPrice(rs.getFloat(3));
sBean.setType(rs.getString(4));
sBean.setNumber(rs.getInt(5));
sBean.setMakeTime(rs.getString(6));
sBean.setUseDay(rs.getInt(7));
list.add(sBean);
}
return list;
}软件报的错误如下----"com.microsoft.sqlserver.jdbc.SQLServerException: 由 ORDER BY 编号 1 标识的 SELECT 项包含一个变量,作为标识列位置的表达式的一部分。按照引用列名的表达式排序时,只允许使用变量。"希望达人点化下!
public class StorageDaoImpl extends BaseDao implements StorageDao {
private Connection con=null;
private PreparedStatement pstmt=null;
private ResultSet rs=null;
private String sql=null;
private String[] str={"name","price","number","makeTime","电器","食品","服装","日用品"};
private List<StorageBean> list=new ArrayList<StorageBean>();
private StorageBean sBean=null; public List<StorageBean> getStorage(int id) throws Exception {
con=this.getConnection();
if(id<5){
//sql语句是我如此构建的 如果直接sql="select * from storage order by name";运行能成功,
//但是下面这样就不可以?这是为什么?
sql="select * from storage order by ?";
pstmt=con.prepareStatement(sql);
pstmt.setString(1, str[id-1]);
}else {
sql="select * from storage where type like ?";
pstmt=con.prepareStatement(sql);
pstmt.setString(1, str[id-1]);
}
rs=pstmt.executeQuery();
while(rs.next()){
sBean=new StorageBean();
sBean.setId(rs.getInt(1));
sBean.setName(rs.getString(2));
sBean.setPrice(rs.getFloat(3));
sBean.setType(rs.getString(4));
sBean.setNumber(rs.getInt(5));
sBean.setMakeTime(rs.getString(6));
sBean.setUseDay(rs.getInt(7));
list.add(sBean);
}
return list;
}软件报的错误如下----"com.microsoft.sqlserver.jdbc.SQLServerException: 由 ORDER BY 编号 1 标识的 SELECT 项包含一个变量,作为标识列位置的表达式的一部分。按照引用列名的表达式排序时,只允许使用变量。"希望达人点化下!
如果要用PreparedStatement的话,上面的写法明显是错误的
一个正确的写法例子如下:
select * from storage where 字段=?
然后设置该字段的参数值
pstmt.setString(1, str[id-1]);
1)select * from storage order by 语句中by之后只能是变量.而你用prepareStatement的setString()实际上生成的是:select * from storage order by "name" --这是一个值
2)因此:你只好用SQL语句的拼接了,如:
sql="select * from storage order by "+ str[id-1]);
sql="select * from storage order by ?";
pstmt=con.prepareStatement(sql);
pstmt.setString(1, str[id-1]);
这里的str[id-1]是常量name,而sql要求order by接的是变量,自然报错,
而你用sql="select * from storage order by name";时,这里的name是一个列的名字,不是常量,所以是正确的
《---select * from storage order by 语句中by之后只能是变量.而你用prepareStatement的setString()实际上生成的是:select * from storage order by "name" --这是一个值 ----》 如是说需要接的是个变量 那我代码做如下改动 //这里的a 应该算变量吧 因为它的值是没有固定下来的,是根据 Str[id-1];来确定的
//那下面 order by 后面接的就应该是个变量啊, 可是还是报错。
String a=str[id-1];
sql="select * from storage order by ?";
//sql="select * from storage order by"+str[id-1];
pstmt=con.prepareStatement(sql); pstmt.setString(1,a);
所以我想明确的是, 是不是 类似于 order by 的后面不能使用 占位符 ?
而不是说 这后面接的应该是变量
我就是在这里有点糊涂了!
改成的确实是平凑出来的 sql语句 sql="select * from storage order by "+ str[id-1]);
不过还是很希望能搞清楚 到底是为什么不能那样写
如果你写成:public List<StorageBean> getStorage(int id) throws Exception {
con=this.getConnection();
if(id<5){
sql="select * from storage order by ?";
pstmt=con.prepareStatement(sql);
pstmt.setString(1, id);
}else {
就没问题,这个id就是变量