问题:sqlserver查询中文:䱗、 䱨 ,查不出来!
而且在后缀名.sql 和.txt文件保存变成问号,需要将编码改为为UTF-8,才能正确保存。
一、测试案例:
create table t2(
id int,
name nvarchar(50) not null,
)
insert into t2 values(1,N'好')
insert into t2 values(2,N'的')
insert into t2 values(3,N'䱗')
insert into t2 values(4,N'䱨')
--注意insert一定要带N,且字符串类型为nvarchar,否则sqlserver显示是问号?
select *from t2 where name =N'䱗'
结果错误
3 䱗
4 䱨
--等同于查询空字符串
select *from t2 where name =N''
3 䱗
4 䱨
--解决方案一:修改某张表某个字段的排序规则
ALTER TABLE t2 ALTER COLUMN name nvarchar(50) COLLATE Chinese_PRC_BIN --中文简体 二进制排序规则
select *from t2 where name =N'䱗'
结果正确
3 䱗
--注意如果此时name 字段not null会变成null,要改回来。
--但是不能用下面的sql语句,这会导致排序规则变成Chinese_PRC_CI_AS,只能用表设计器(选中表-右键-设计-改为非空)。
ALTER TABLE t2 ALTER COLUMN name nvarchar(50) not null
--解决方案二:
--如果不想修某张表某个字段的排序规则,可以查询是添加 COLLATE Chinese_PRC_BIN
--先恢复成原始排序规则
ALTER TABLE t2 ALTER COLUMN name nvarchar(50) COLLATE Chinese_PRC_CI_AS -- 中文简体 不区分大小写、区分重音、不区分假名、不区分全半角
select * from t2 where name = N'䱨' COLLATE Chinese_PRC_BIN
查询结果正确:
4 䱨
--解决方案三:
--创建的时候 直接设置某张表某字段排序规则
delete from t2
create table t1(
id int,
name varchar(50) collate Chinese_PRC_BIN --not null 需要另外设置
)
ALTER TABLE t2 ALTER COLUMN name nvarchar(50) not null
--解决方案四: 针对Entity Framework 6 (没有去测试)
1直接写存sql参数化语句查询
string name="䱨"
var sql = "select * from t2 where name like N'%@name%' or [name2] like N'%@name%'"
// 如果@name有问题可以尝试
string name=“%”+“䱨”+“%”
var sql = "select * from t2 where name like N'@name' or [name2] like N'@name'"
或string name= “N‘%䱨%’”
var sql = "select * from t2 where name like @name or [name2] like @name"
var sqlParams = new SqlParameter[]
{
new SqlParameter("@name",System.Data.SqlDbType.Nvarchar) {Value= name}
};
var data = db.Database.SqlQuery<t2Temp>(sql, sqlParams);
t2Temp是数据接收类,能存储查询结果就行。
2、sql非参数化查询语句
string name="䱨"
var sql = "select * from t2 where name like N'%"+name+"%' or [name2] like N'%"+name+"%'"
var data = db.Database.SqlQuery<t2Temp>(sql, sqlParams);
但要注意对name做校验,防止sql注入攻击。
--解决方案五: 针对Entity Framework Core (没有去测试)
1查询中的显式排序规则
var customers = context.Customers
.Where(c => EF.Functions.Collate(c.Name, "SQL_Latin1_General_CP1_CS_AS") == "John") //sql排序规则可能不对应
.ToList();
2列排序规则
使用EF Core管理数据库架构时,以下内容将 属性的 列配置为不区分大小写,而该数据库已配置为区分 Name 大小写:
modelBuilder.Entity<Customer>().Property(c => c.Name)
.UseCollation("SQL_Latin1_General_CP1_CI_AS");
3数据库排序规则
使用EF Core管理数据库架构时,模型的 方法中的以下内容将SQL Server OnModelCreating 数据库配置为使用区分大小写的排序规则:
modelBuilder.UseCollation("SQL_Latin1_General_CP1_CS_AS");
--注意 多字段或查询会出问题
drop table t2
create table t2(
id int,
name nvarchar(50) collate Chinese_PRC_BIN,
name2 nvarchar(50) not null
)
insert into t2 values(1,N'好',N'管控')
insert into t2 values(2,N'的',N'根据')
insert into t2 values(3,N'䱗',N'开天眼')
insert into t2 values(4,N'䱨',N'返回')
select * from t2
select * from t2 where name like N'%䱗%' or name2 LIKE N'%䱗%'
结果如下:
1 好 管控
2 的 根据
3 䱗 开天眼
4 䱨 返回
解决方案是:
1不改数据库每次查询都带上Chinese_PRC_BIN
select * from t2 where name like N'%䱗%' or [name2] like N'%䱗%' collate Chinese_PRC_BIN
结果如下:
3 䱗 开天眼
2把所有where条件出现的字段 排序规则都改为 Chinese_PRC_BIN
ALTER TABLE t2 ALTER COLUMN name2 nvarchar(50) COLLATE Chinese_PRC_BIN
select * from t2 where name like N'%䱗%' or [name2] like N'%䱗%'
结果如下:
3 䱗 开天眼
相关文档:
COLLATE语法介绍
https://docs.microsoft.com/zh-cn/sql/t-sql/statements/collations?view=sql-server-ver15
sqlserver 排序规则介绍:
https://docs.microsoft.com/zh-cn/sql/relational-databases/collations/collation-and-unicode-support?view=sql-server-ver15
EF6、EFCode 排序规则介绍
https://docs.microsoft.com/zh-cn/ef/core/miscellaneous/collations-and-case-sensitivity
https://www.bookstack.cn/read/ef-core-zh/36b68308cefb1f5b.md
同类文章:
SQL SERVER 生僻字查询问题和关键字COLLATE
https://blog.csdn.net/sinat_28984567/article/details/109253444
https://blog.csdn.net/johnf_nash/article/details/78947219