2016-11-15 1 views
0

값 있어요 사양 제목, 값 및 "~"로 구분 된 선택 매개 변수로 0 또는 1 (1이면 빠뜨림)이고 ech 옵션은^표 열은 다른 컬럼 값에 의해 분할하며

에 의해 구분됩니다.

SKU 및 각 사양 제목으로 테이블로 분할하고 싶습니다. 열 머리글 및 값을 값으로 사용

훨씬 간단

나는 뛰어 사양 기록으로 분할하고 각 규격 및 레코드 값에서 제목을 분리하는 방법이

let 
    Source = Excel.CurrentWorkbook(){[Name="Таблица1"]}[Content], 
    Type = Table.TransformColumnTypes(Source,{{"Part Number", type text}, {"Specifications", type text}}), 
    #"Replaced Value" = Table.ReplaceValue(Type,"Specification##","",Replacer.ReplaceText,{"Specifications"}), 
    SplitByDelimiter = (table, column, delimiter) => 
     let 
      Count = List.Count(List.Select(Text.ToList(Table.Column(table, column){0}), each _ = delimiter)) + 1, 
      Names = List.Transform(List.Numbers(1, Count), each column & "." & Text.From(_)), 
      Types = List.Transform(Names, each {_, type text}), 
      Split = Table.SplitColumn(table, column, Splitter.SplitTextByDelimiter(delimiter), Names), 
      Typed = Table.TransformColumnTypes(Split, Types) 
     in 
      Typed, 
    Split = SplitByDelimiter(#"Replaced Value","Specifications","^"), 
    Record = Table.ToRecords(Split) 
in 
    Record 
+0

[이 질문에] 좋은 대답이 있습니다. (http://stackoverflow.com/questions/36918354/extract-mobile-numbers-to-other-cells-in-excel) 구분 기호. 거기에있는 첫 번째 VBA UDF는 매우 쉽게 필요한 것을 수행 할 수 있으며 매우 가볍습니다. – JNevill

+2

샘플 테이블을 코드로 제공해 주실 수 있습니까? Table.FromRecords 또는 #table ({}, {{}})을 사용하십시오. –

+0

Sergey와 동의 한 후 입력 데이터의 스크린 샷을 게시하지 마십시오. 또한 코드가 오늘 반환하는 것을 게시 할 수 있으며 반환 할 출력을 원하는대로 지정할 수 있습니까? –

답변

1

좋아, 나는 이것이 저녁 내내 소요 된 것처럼 여전히 필요하다고 희망한다. :)) 아주 재미있는 작업을해야합니다!

나는, "~ 1"은 항상 와 함께 "^" 결합되도록 "1 ~ ^" 항상 끝 필드의 값을 가정합니다. 또한 모든 콜론이 제거되었으므로 ":"이 값으로 존재하지 않는다고 가정합니다.

IMO에서는 Table.SplitColumn 함수를 전혀 사용할 필요가 없습니다.

let 
    //replace it with your Excel.CurrentWorkbook(){[Name="Таблица1"]}[Content], 
    Source = #table(type table [Part Number = Int64.Type, Specifications = text], {{104, "Model:~104~1^Type:~Watch~1^Metal Type~Steel~1"}, {105, "Model:~105~1^Type:~Watch~1^Metal Type~Titanium~1^Gem Type~Ruby~1"}}), 

    //I don't know why do you replace these values, do you really need this? 
    ReplacedValue = Table.ReplaceValue(Source,"Specification##","",Replacer.ReplaceText,{"Specifications"}), 
    TransformToLists = Table.TransformColumns(Source, {"Specifications", each List.Transform(List.Select(Text.Split(_ & "^", "~1^"), each _ <> "") , each Text.Split(Text.Replace(_, ":", ""), "~")) }), 
    ConvertToTable = Table.TransformColumns(TransformToLists, {"Specifications", each Table.PromoteHeaders(Table.FromColumns(_))}), 
    ExpandedSpecs = Table.TransformRows(ConvertToTable, (x) => Table.ExpandTableColumn(Table.FromRecords({x}), "Specifications", Table.ColumnNames(x[Specifications]))), 
    UnionTables = Table.Combine(ExpandedSpecs), 
    Output = UnionTables 
in 
    Output 

UPDATE : 작동 원리

(건너 뛰는 명백한 단계) :

TransformToLists : TransformColumns 테이블 소요되며, 이 적용 열 이름과 함수 목록 열 값입니다. 따라서 은 각 행의 "Specifications"필드에 몇 개의 중첩 된 함수를 적용합니다.. List.Select 순서대로 "규격"의 값 Text.Split 함수를 적용하여 얻었다 비어 값의리스트를 반환 갖는 필드 :이 함수는 다음과 같이 ":"s의 제거 :

Text.Split(
       Text.Replace(_, ":", "") 
       , "~") 

각 키워드는 밑줄 기호로 표시된 모든 처리 된 값 (필드, 열, 행/레코드, 목록 항목, 텍스트, 함수 등일 수 있음)에 적용된 다음 기능을 의미합니다. 이 밑줄이 기능을 대체 할 수 있습니다 : "부품 번호"와 "사양"포함 목록 : 미루어

each _ equals (x) => some_function_that_returns_corresponding_value(x) 

그래서,

each Text.Replace(_, ":", "") 
     equals 
    (x) => Text.Replace(x, ":", "") //where x is any variable name. 

    //You can go further and make it typed, although generally it is not needed: 
    (x as text) => Text.Replace(x, ":", "") 

    //You can also write a custom function and use it: 
    (x as text) => CustomFunctionName(x) 

, TransformToLists 단계는 두 개의 열이있는 테이블을 리턴 목록. 이러한 각 목록에는 열 이름과 해당 값의 두 가지 값이 있습니다.이는 "사양"필드의 초기 값이 두 번 나누어 져야하기 때문에 발생합니다. 먼저 "~ 1 ^"로 쌍으로 분할 한 다음 각 쌍을 "~"로 분할합니다. 이제는 각 중첩 목록에 열 이름과 그 값이 있습니다. 이제는 이들을 모두 하나의 테이블로 변환해야합니다.

ConvertToTable : 우리는 각 행의 "사양"필드에 대한 기능 (기억, 목록의 목록)을 사용하여, 다시 TransformColumns을 적용합니다. 우리는 Table.FromColumns를 사용합니다. 목록으로 인수 목록을 취하고 첫 번째 행이 열 머리글이고 두 번째가 해당 값인 테이블을 반환합니다. 그런 다음 첫 번째 행을 헤더로 승격합니다. 이제 우리는 테이블을 가지며, "Specifications"필드는 가변 개수의 열을 가진 중첩 테이블을 포함합니다. 그리고 우리는 그것들을 모두 모아야합니다.

ExpandedSpecs : Table.TransformRows는 (그것이 X로 서명 된 코드)는 테이블 (레코드)를 각 행으로 변환 함수를 적용한다.

= Table.ExpandTableColumn(//this function expands nested table. It needs a table, but "x" that we have is a record. So we do the conversion: 
    Table.FromRecords({x}) //function takes a list of records, so {x} means a list with single value of x 
    , "Specifications" //Column to expand 
    , Table.ColumnNames(x[Specifications]) //3rd argument is a list of resulting columns. It takes table as an argument, and table is contained within "Specifications" field. 
) 

그것은 (각 단일 행을 가짐) 테이블의 목록을 반환, 우리는 UnionTables 단계에서 Table.Combine를 사용하여 결합 : 내가 그랬던 것처럼 당신은 사용자 정의 함수를 작성할 수 있습니다. 결과적으로 결합 된 테이블의 모든 컬럼을 갖는 테이블이 만들어지며 일부 테이블에는 그러한 컬럼이없는 경우 널 (null)이됩니다.

희망이 있습니다. :)

+0

모양이 작동합니다. 중복 된 열 "부품 번호"에 대한 오류가 발생하지만 해결했습니다. ** "~ 1"**은 항상 사양에있는 것은 아니지만 그래, 항상 ** "^"** 전입니다. "each", char "_"및이 수축 "(x) => Table.ExpandTableColumn"을 사용하여 몇 가지를 설명해 주시겠습니까 – NogrTL

+0

나는 대답을 편집하고 자세한 설명을 추가했습니다. – Eugene

+0

Thx. 이제이 각 명령의 구문을 이해할 수있는 기회를 갖습니다. – NogrTL

0

TextToColumns VBA 솔루션과 함께 도움을 찾고 스택이 코드를 작성 관리 내가 무엇을 요구하는지 이해하면 MSDN for Range.TextToColumns

+0

그것은 보통 스플릿이고 Power 쿼리의 "SplitTextByDelimiter"와 같으며 Spec-Title을 Value에서 분할하고 부품 번호를 참조 할 기회가 없습니다. 그리고 그것을 나눠주고 싶습니다 (예를 들어 - 테이블의 첫 번째 행) "부품 번호", "모델"그리고 모델 번호의 부품 번호와 값을 셀에 표시하면 행을 지정하십시오. – NogrTL

관련 문제