首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >排序顺序与来自MS-Access vs .NET的相同查询不同

排序顺序与来自MS-Access vs .NET的相同查询不同
EN

Stack Overflow用户
提问于 2013-09-22 22:03:30
回答 1查看 1.2K关注 0票数 4

我正在将遗留访问应用程序移植到.NET框架,并且需要维护相同的数据排序顺序。ACCESS应用程序连接到同一个数据库,使用如下配置的ODBC连接:

Microsoft SQL Server本机客户端版本11.00.2100 数据源名称:中央主机集数据库 数据源说明: 服务器: localhost\sqlexpress 使用综合安全:是 数据库: CentralSQL15 语言:(默认) 数据加密:否 信任服务器证书:否 多个活动结果集(MARS):否 镜像服务器: 翻译字符数据:是的 记录长期运行的查询:否 日志驱动程序统计:否 使用区域设置:否 使用ANSI引号标识符:是 使用ANSI Null,Paddings和警告:是

在.NET应用程序中,我最初使用的是带有到Server的连接字符串的SqlClient,但是我也尝试使用OdbcConnection/OdbcCommand/OdbcDataReader,使用与Access完全相同的ODBC连接。但是,在ACCESS和.NET之间排序顺序总是不同的。

例如,通过查询:

代码语言:javascript
复制
SELECT sessionstn3270.sessionid, 
       sessionnames.sessionname, 
       sessionstn3270.sessiontypeid, 
       sessionstn3270.usernameid, 
       sessionnames.host, 
       sessionnames.port, 
       lus.lu, 
       sessionnames.lastmodifiedsn, 
       templates.template, 
       templates.templatetype, 
       sessionnames.sessiontype 
FROM   (sessionnames 
        LEFT JOIN templates 
               ON sessionnames.template = templates.templateid) 
       INNER JOIN (sessionstn3270 
                   LEFT JOIN lus 
                          ON sessionstn3270.sessionid = lus.sessionid) 
               ON sessionnames.sessionnameid = sessionstn3270.sessionnameid 
WHERE  usernameid = 3978 
ORDER  BY templates.templatetype, 
          sessionnames.sessiontype; 

使用和.NET应用程序,SessionID按以下顺序返回:

代码语言:javascript
复制
17797
17798
17799
17800
17801
105372

在MS Access中,它们按以下顺序返回:

代码语言:javascript
复制
17801
17800
17999
17998
17797
105372

95%的时间,我可以通过添加ORDER BY SessionID DESC复制相同的搜索结果,但不是100%,我尝试过不同字段的不同排序顺序,但没有一个能100%工作。

有人知道还有什么会影响Access和.NET之间返回的结果顺序吗?

我从ExpressProfiler下载了http://expressprofiler.codeplex.com/,发现了以下内容:

当Access向ACCESS数据库发送SQL查询时,会发生以下事务:

代码语言:javascript
复制
SELECT "dbo"."SessionsTN3270"."SessionID" ,"dbo"."SessionsTN3270"."SessionID","dbo"."SessionNames"."SessionType" ,"dbo"."SessionNames"."SessionNameID","dbo"."Templates"."TemplateType" ,"dbo"."Templates"."TemplateID" FROM "dbo"."SessionsTN3270",\oj "dbo"."SessionNames" LEFT OUTER JOIN "dbo"."Templates" ON ("dbo"."SessionNames"."Template" = "dbo"."Templates"."TemplateID" ) \ WHERE (("dbo"."SessionsTN3270"."UserNameID" = 3978 ) AND ("dbo"."SessionNames"."SessionNameID" = "dbo"."SessionsTN3270"."SessionNameID" ) ) 
go
declare @p1 int
set @p1=1
exec sp_prepexec @p1 output,N'@P1 int',N'SELECT "SessionID" ,"dbo"."LUs"."LUID" FROM "dbo"."LUs"  WHERE ("SessionID" = @P1)',17797
select @p1
go
exec sp_execute 1,17798
go
exec sp_execute 1,17799
go
exec sp_execute 1,17800
go
exec sp_execute 1,17801
go
exec sp_execute 1,105372
go
SELECT CASE DATABASEPROPERTYEX( DB_NAME(), 'Updateability') WHEN 'READ_ONLY' THEN 'Y' ELSE 'N' END
go
declare @p1 int
set @p1=1
exec sp_prepexec @p1 output,N'@P1 int,@P2 int,@P3 int,@P4 int,@P5 int,@P6 int,@P7 int,@P8 int,@P9 int,@P10 int',N'SELECT "TemplateID","Template","TemplateType"  FROM "dbo"."Templates"  WHERE "TemplateID" = @P1 OR "TemplateID" = @P2 OR "TemplateID" = @P3 OR "TemplateID" = @P4 OR "TemplateID" = @P5 OR "TemplateID" = @P6 OR "TemplateID" = @P7 OR "TemplateID" = @P8 OR "TemplateID" = @P9 OR "TemplateID" = @P10',15,15,15,15,15,33,33,33,33,33
select @p1
go
declare @p1 int
set @p1=2
exec sp_prepexec @p1 output,N'@P1 int,@P2 int,@P3 int,@P4 int,@P5 int,@P6 int,@P7 int,@P8 int,@P9 int,@P10 int',N'SELECT "SessionNameID","SessionName","Host","Template","SessionType","Port","LastModifiedSN","SSMA_TimeStamp"  FROM "dbo"."SessionNames"  WHERE "SessionNameID" = @P1 OR "SessionNameID" = @P2 OR "SessionNameID" = @P3 OR "SessionNameID" = @P4 OR "SessionNameID" = @P5 OR "SessionNameID" = @P6 OR "SessionNameID" = @P7 OR "SessionNameID" = @P8 OR "SessionNameID" = @P9 OR "SessionNameID" = @P10',204,203,202,201,200,272,272,272,272,272
select @p1
go
declare @p1 int
set @p1=3
exec sp_prepexec @p1 output,N'@P1 int,@P2 int,@P3 int,@P4 int,@P5 int,@P6 int,@P7 int,@P8 int,@P9 int,@P10 int',N'SELECT "SessionID","SessionTypeID","UserNameID","SessionNameID"  FROM "dbo"."SessionsTN3270"  WHERE "SessionID" = @P1 OR "SessionID" = @P2 OR "SessionID" = @P3 OR "SessionID" = @P4 OR "SessionID" = @P5 OR "SessionID" = @P6 OR "SessionID" = @P7 OR "SessionID" = @P8 OR "SessionID" = @P9 OR "SessionID" = @P10',17801,17800,17799,17798,17797,105372,105372,105372,105372,105372
select @p1
go
declare @p1 int
set @p1=4
exec sp_prepexec @p1 output,N'@P1 int,@P2 int,@P3 int,@P4 int,@P5 int,@P6 int,@P7 int,@P8 int,@P9 int,@P10 int',N'SELECT "LUID","SessionID","LU"  FROM "dbo"."LUs"  WHERE "LUID" = @P1 OR "LUID" = @P2 OR "LUID" = @P3 OR "LUID" = @P4 OR "LUID" = @P5 OR "LUID" = @P6 OR "LUID" = @P7 OR "LUID" = @P8 OR "LUID" = @P9 OR "LUID" = @P10',18539,18539,18539,18539,18539,18539,18539,18539,18539,18539
select @p1
go
SELECT "SessionTypeID" ,"SessionType"  FROM "dbo"."SessionTypes" WHERE ("HostTypeID" = 200 ) 
go
SELECT "UserNameID" ,"WSUserName" ,"RecordType" ,"Role" ,"SecurityLevel" ,"BuildingCode" ,"FloorLevel" ,"ServerID" ,"Airline" ,"Description" ,"LastModified"  FROM "dbo"."WSUsers" 
go

但是,当Server运行查询时,它要简单得多:

代码语言:javascript
复制
SELECT SessionsTN3270.SessionID, SessionNames.SessionName, SessionsTN3270.SessionTypeID, SessionsTN3270.UserNameID, SessionNames.Host, SessionNames.Port, LUs.LU, SessionNames.LastModifiedSN, Templates.Template, Templates.TemplateType, SessionNames.SessionType

FROM (SessionNames LEFT JOIN Templates ON SessionNames.Template = Templates.TemplateID) INNER JOIN (SessionsTN3270 LEFT JOIN LUs ON SessionsTN3270.SessionID = LUs.SessionID) ON SessionNames.SessionNameID = SessionsTN3270.SessionNameID WHERE UserNameID = 3978 ORDER BY Templates.TemplateType, SessionNames.SessionType;

go

从这个SQL跟踪中,我发现我可以使用查询从SQL服务器复制相同的顺序,如下所示:

代码语言:javascript
复制
SELECT "dbo"."SessionsTN3270"."SessionID" ,"dbo"."SessionsTN3270"."SessionID","dbo"."SessionNames"."SessionType" ,"dbo"."SessionNames"."SessionNameID","dbo"."Templates"."TemplateType" ,"dbo"."Templates"."TemplateID" FROM "dbo"."SessionsTN3270", "dbo"."SessionNames" LEFT OUTER JOIN "dbo"."Templates" ON ("dbo"."SessionNames"."Template" = "dbo"."Templates"."TemplateID" ) 
 WHERE (("dbo"."SessionsTN3270"."UserNameID" = 3978 ) AND ("dbo"."SessionNames"."SessionNameID" = "dbo"."SessionsTN3270"."SessionNameID" ) ) 
EN

回答 1

Stack Overflow用户

发布于 2013-09-23 01:22:09

解决方案是使用ExpressProfiler (http://expressprofiler.codeplex.com/),如果您有完整的SQL,请使用包含在SQL中的SQL。通过使用ExpressProfiler跟踪查询,我能够匹配ACCESS使用的查询,因为ACCESS在发送到server之前修改了SQL查询,这样我就可以按照相同的顺序获得结果。我在这篇博客文章中提到的全部细节:http://chentiangemalc.wordpress.com/2013/09/23/case-of-the-sql-vs-access-sort-order/

票数 4
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18949232

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档