Quando devemos usar NVARCHAR / NCHAR em vez de VARCHAR / CHAR no SQL Server?

Existe uma regra quando devemos usar os tipos Unicode?

Eu vi que a maioria dos idiomas europeus (alemão, italiano, inglês, …) estão bem no mesmo database em colunas VARCHAR.

Eu estou procurando por algo como:

  1. Se você tem chinês -> use NVARCHAR
  2. Se você tem alemão e árabe -> use NVARCHAR

E quanto ao agrupamento do servidor / database?

Eu não quero usar sempre NVARCHAR como sugerido aqui Quais são as principais diferenças de desempenho entre os tipos de dados varchar e nvarchar do SQL Server?

A verdadeira razão que você quer usar NVARCHAR é quando você tem diferentes idiomas na mesma coluna, você precisa abordar as colunas em T-SQL sem decodificação, você quer ser capaz de ver os dados “nativamente” no SSMS, ou você quer para padronizar em Unicode.

Se você tratar o database como armazenamento burro, é perfeitamente possível armazenar strings amplas e codificações diferentes (até de comprimento variável) em VARCHAR (por exemplo, UTF-8). O problema surge quando você está tentando codificar e decodificar, especialmente se a página de códigos for diferente para linhas diferentes. Isso também significa que o SQL Server não será capaz de lidar com os dados facilmente para fins de consulta no T-SQL em colunas (potencialmente variables) codificadas.

Usando NVARCHAR evita tudo isso.

Eu recomendaria NVARCHAR para qualquer coluna que tenha dados inseridos pelo usuário, o que é relativamente irrestrito.

Eu recomendaria VARCHAR para qualquer coluna que é uma chave natural (como uma placa de veículo, SSN, número de série, etiqueta de serviço, número de ordem, indicativo de aeroporto, etc) que é tipicamente definida e limitada por um padrão ou legislação ou convenção. Também VARCHAR para usuário inserido, e muito restrito (como um número de telefone) ou um código (ACTIVE / CLOSED, Y / N, M / F, M / S / D / W, etc). Não há absolutamente nenhuma razão para usar o NVARCHAR para eles.

Então, para uma regra simples:

VARCHAR quando garantido para ser limitado NVARCHAR de outra forma

Você deve usar NVARCHAR sempre que precisar armazenar vários idiomas. Eu acredito que você tem que usá-lo para os idiomas asiáticos, mas não me cite sobre isso.

Aqui está o problema se você pegar russo por exemplo e armazená-lo em um varchar, você ficará bem desde que você defina a página de código correta. Mas digamos que você esteja usando uma instalação padrão do sql em inglês, então os caracteres russos não serão manipulados corretamente. Se você estivesse usando NVARCHAR (), eles seriam manipulados corretamente.

Editar

Ok, deixe-me citar MSDN e maybee eu era específico, mas você não quer armazenar mais de uma página de código em uma coluna varcar, enquanto você pode não deve

Quando você lida com dados de texto armazenados no tipo de dados char, varchar, varchar (max) ou texto, a limitação mais importante a considerar é que somente as informações de uma única página de código podem ser validadas pelo sistema. (Você pode armazenar dados de várias páginas de código, mas isso não é recomendado.) A página de código exata usada para validar e armazenar os dados depende do agrupamento da coluna. Se um agrupamento em nível de coluna não tiver sido definido, o agrupamento do database será usado. Para determinar a página de código usada para uma determinada coluna, você pode usar a function COLLATIONPROPERTY, conforme mostrado nos exemplos de código a seguir:

Aqui está mais um pouco:

Este exemplo ilustra o fato de que muitas localidades, como georgiano e hindi, não têm páginas de código, pois são agrupamentos somente Unicode. Esses agrupamentos não são apropriados para colunas que usam o tipo de dados char, varchar ou text

Então georgiano ou hindi realmente precisa ser armazenado como nvarchar. O árabe também é um problema:

Outro problema que você pode encontrar é a incapacidade de armazenar dados quando nem todos os caracteres que você deseja suportar estão contidos na página de código. Em muitos casos, o Windows considera uma determinada página de código como uma página de código “melhor ajuste”, o que significa que não há garantia de que você pode confiar na página de código para manipular todo o texto; é meramente o melhor disponível. Um exemplo disso é o script árabe: ele suporta uma ampla gama de idiomas, incluindo Baluchi, Berber, Farsi, Caxemira, Cazaque, Quirguiz, Pashto, Sindi, Uighur, Urdu e muito mais. Todos esses idiomas têm caracteres adicionais além daqueles no idioma árabe, conforme definido na página de código 1256 do Windows. Se você tentar armazenar esses caracteres extras em uma coluna não-Unicode que tenha o agrupamento em árabe, os caracteres serão convertidos em pontos de interrogação.

Algo para manter em mente quando você estiver usando Unicode, embora você possa armazenar diferentes idiomas em uma única coluna, você só pode classificar usando um único agrupamento. Existem alguns idiomas que usam caracteres latinos, mas não se classificam como outros idiomas latinos. Acentos é um bom exemplo disso, não consigo me lembrar do exemplo, mas havia uma língua do leste europeu cujo Y não se parecia com o inglês Y. Depois, há o espanhol que os usuários espanhóis expetam para serem classificados depois de h.

Tudo sumdo com todos os problemas que você tem que lidar quando se trata de internalicionalização. É minha opinião que é mais fácil usar apenas caracteres Unicode desde o início, evitar as conversões extras e aproveitar o espaço atingido. Daí minha declaração anterior.

O grego precisaria de UTF-8 em N tipos de coluna: αβγ;)

Josh diz: “…. Algo para manter em mente quando você está usando Unicode, embora você possa armazenar diferentes idiomas em uma única coluna, você só pode classificar usando um único agrupamento. Há alguns idiomas que usam caracteres latinos, mas não se classificam como Destaques é um bom exemplo disso, não posso me lembrar do exemplo, mas havia uma língua européia oriental cujo Y não se parecia com o inglês Y. Então há o espanhol que os usuários espanhóis expetam para serem classificados depois de h. ”

Eu sou um falante nativo de espanhol e “ch” não é uma letra, mas dois “c” e “h” e o alfabeto espanhol é como: abcdefghijklmn ñ opqrstuvwxyz Nós não esperamos “ch” depois de “h” mas “i” O alfabeto é o mesmo que em inglês, exceto para o ñ ou em HTML “& ntilde;”

Alex

TL; DR;
Unicode – (nchar, nvarchar e ntext)
Não unicode – (char, varchar e texto).

Do MSDN

Agrupamentos no SQL Server fornecem regras de sorting, caso e propriedades de sensibilidade de acento para seus dados. Agrupamentos que são usados ​​com tipos de dados de caractere, como char e varchar, ditam a página de código e os caracteres correspondentes que podem ser representados para esse tipo de dados.

Supondo que você esteja usando o agrupamento SQL padrão SQL_Latin1_General_CP1_CI_AS , o script a seguir deve imprimir todos os símbolos que você pode ajustar em VARCHAR pois usa um byte para armazenar um caractere (total de 256) se você não o visualizar na lista impressa. NVARCHAR .

 declare @i int = 0; while (@i < 256) begin print cast(@i as varchar(3)) + ' '+ char(@i) collate SQL_Latin1_General_CP1_CI_AS print cast(@i as varchar(3)) + ' '+ char(@i) collate Japanese_90_CI_AS set @i = @i+1; end 

Se você alterar o agrupamento para digamos japonês, você notará que todas as estranhas letras européias se tornaram normais e alguns símbolos ? marcas.

Unicode é um padrão para mapear pontos de código para caracteres. Como foi projetado para abranger todos os caracteres de todos os idiomas do mundo, não há necessidade de páginas de código diferentes para lidar com diferentes conjuntos de caracteres. Se você armazenar dados de caracteres que refletem vários idiomas, sempre use os tipos de dados Unicode (nchar, nvarchar e ntext) em vez dos tipos de dados não-Unicode (char, varchar e text).

Caso contrário, sua sorting será esquisita.

    Intereting Posts