Tsql sql-如何将全名拆分为名字和姓氏

Tsql sql-如何将全名拆分为名字和姓氏,tsql,Tsql,如果我有一个包含全名的列的表,例如: fullname ------------ Joe Bloggs Peter Smith Mary Jones and Liz Stone 如何使用SQL从“全名”列中的每个条目中重试名字和姓氏。我不担心我的例子中第三个条目中的第二个名字,即Liz Stone 所以基本上是为了取回 Firstname --------- Joe Peter Mary Lastname -------- Bloggs Smith Jones 你可以用 STRIN

如果我有一个包含全名的列的表,例如:

fullname
------------
Joe Bloggs
Peter Smith
Mary Jones and Liz Stone
如何使用SQL从“全名”列中的每个条目中重试名字和姓氏。我不担心我的例子中第三个条目中的第二个名字,即Liz Stone

所以基本上是为了取回

Firstname
---------
Joe
Peter
Mary

Lastname  
--------
Bloggs 
Smith
Jones
你可以用

 STRING_SPLIT (string , separator)

下面是一个SQL Server 2016之前的方法,它使用基本字符串函数来隔离名字和姓氏

SELECT SUBSTRING(fullname, 1, CHARINDEX(' ', fullname) - 1) AS Firstname,     
       SUBSTRING(fullname,
                 CHARINDEX(' ', fullname) + 1,
                 LEN(fullname) - CHARINDEX(' ', fullname)) AS Lastname
FROM yourTable

请注意,此解决方案假定
全名
列只包含一个名字和一个姓氏(即没有中间名、首字母缩写等)。

这是一个滑坡,没有简单的答案。也就是说,考虑下面的

Declare @YourTable table (FullName varchar(50))
Insert Into @YourTable values
('Joe Bloggs'),
('Peter Smith'),
('Betty Jane Martinez'),
('Mary Jones and Liz Stone')


Select A.*
      ,FirstName = Pos1+case when Pos3 is not null then ' '+Pos2 else '' end
      ,LastName  = case when Pos3 is null then Pos2 else Pos3 end
 From @YourTable A
 Cross Apply (
    Select Pos1 = xDim.value('/x[1]','varchar(max)')
          ,Pos2 = xDim.value('/x[2]','varchar(max)')
          ,Pos3 = xDim.value('/x[3]','varchar(max)')
          ,Pos4 = xDim.value('/x[4]','varchar(max)')
          ,Pos5 = xDim.value('/x[5]','varchar(max)')
          ,Pos6 = xDim.value('/x[6]','varchar(max)')
     From  (Select Cast('<x>' + replace((Select substring(FullName,1,charindex(' and ',FullName+' and ')-1) as [*] For XML Path('')),' ','</x><x>')+'</x>' as xml) as xDim) as A 
 ) B
如果有助于视觉效果,则会生成交叉应用


这是在没有任何假设的情况下回答这个问题最简单、最短的方法。您还可以使用
rtrim(ltrim('firstname-lastname'))
进一步增强这一点

如果字符串前面有空格

Select 
    substring('Firstname Lastname',1,CHARINDEX(' ', 'Firstname Lastname')) as firstname, 
    substring('Firstname Lastname',CHARINDEX(' ', 'Firstname Lastname'),LEN('Firstname Lastname')) as Lastname

我使用这个查询来检索first和lastname

SELECT SUBSTRING(FULLNAME, 1, CASE WHEN CHARINDEX(' ', FULLNAME)>0 THEN CHARINDEX(' ', FULLNAME) - 1 ELSE LEN(FULLNAME) END ) AS Firstname,
  REVERSE(SUBSTRING(REVERSE(FULLNAME), 1, CASE WHEN CHARINDEX(' ', REVERSE(FULLNAME))>0 THEN CHARINDEX(' ', REVERSE(FULLNAME)) - 1 ELSE LEN(REVERSE(FULLNAME)) END ) )AS Firstname FROM  HRMDESFO.EMPLOID


此版本检查全名中是否有要拆分的空格。如果没有,则将名字设置为空字符串,并将全名放入姓氏中。此外,当存在多个空间时,反向用于在最后一个空间上拆分

select  passemail,substring(passemail,1,instr(passemail,'@') - 1) as name ,
substring(passemail,instr(passemail,'@') + 1,length(passemail)) from passenger
substr(名称,1,STRPOS(名称“”)-1)作为名字

substr(名称,STRPOS(名称“”)+1,长度(名称))作为LastName

获取firstName

SELECT SUBSTR(FULLNAME,1,(LOCATE(' ',FULLNAME)))  AS FIRSTTNAME from EmployeeDetails;

SELECT SUBSTR(FULLNAME,(LOCATE(' ',FULLNAME)))  AS LASTNAME from EmployeeDetails;
所以


从表中选择SUBSTR(名称,1,(定位(名称,))作为FIRSTTNAME,选择SUBSTR(名称,(定位(名称,)+1))作为LASTNAME

您使用的是什么版本的SQL server?中间名是什么,例如
John Phillips Souza
?除非您确定每个名字只包含一个名字和姓氏,否则这个问题可能很难解决。中间名不需要:)Sql Server 2016引入了字符串分割方法。为什么
Jones
Stone
而不是
Jones
Liz
Stone
?对于简单的名字、姓氏,拆分字符串是可以原谅的。在这种情况下,虽然您似乎有一些严重的问题,但多人存储在同一行中,这应该是一个注释。如果你想将此作为答案发布,你应该发布一个实际的例子。OP将如何访问姓氏?或者在同样提到的“mr smith and mrs jane”或“Alex smith and alice jane”的情况下,名字可以显示出来,但姓氏还包括合伙人的名字,例如“Jones and Liz Stone”,将
行分成两个记录可能需要自定义函数。如果您确实有这样的边缘情况,我建议您在将数据导入SQL Server之前先清理数据。我们是否可以将“AND”和其后的任何名称替换为您姓氏SQL中的空白字符串?我们是否可以将“AND”替换为空字符串在sql部分中,无论后面是什么名字,后面是一个空白字符串,您是否推断出姓氏?如果查询结果是文本,则应将其发布为文本,而不是截图,请在您的答案中添加解释,以帮助其他人学习。只有代码的答案被认为是不礼貌的。虽然这个答案没有错,但它没有提到使用的SQL方言。字符串函数非常特定于SQL方言:我在标题中提到了BigQuery:StandardSQL方言。column_name:是包含名称的列。table_name:是从中选择列_name的表的名称。请通过添加说明尽最大努力更好地格式化您的答案。
SELECT SUBSTR(FULLNAME,1,(LOCATE(' ',FULLNAME)))  AS FIRSTTNAME from EmployeeDetails;
SELECT SUBSTR(FULLNAME,(LOCATE(' ',FULLNAME)))  AS LASTNAME from EmployeeDetails;
SELECT  SUBSTR(FULLNAME,1,(LOCATE(' ',FULLNAME)))  AS FIRSTTNAME, SUBSTR(FULLNAME,(LOCATE(' ',FULLNAME)))  AS LASTNAME from EmployeeDetails;
SELECT 
  LEFT(column_name,  POSITION(' ' IN column_name)-1)                     AS first_name,
  RIGHT(column_name, LENGTH(column_name) - POSITION(' ' IN column_name)) AS last_name
FROM table_name