Страницы: 1
RSS
Замена текста с помощью List Generator Power query по условию
 
Возможно ли сделать с помощью List Generator или другой функцией Power query замену текста в столбце "Наименование работ, ед. изм.".
Я реализовал это с добавлением столбца [Индекс] и [Пользовательская], хотелось бы уйти от лишних шагов в Power query. Мысль такая, если содержит "В т.ч.", то нижних четыре строчки, после последнего "В т.ч.", тоже должны быть со словом "В т.ч.". Файл приложен с реализацией добавление столбцов.
Код
#"Условный столбец добавлен" = Table.AddColumn(#"Добавлен индекс", "Пользовательская", each try if Text.Contains([#"Наименование работ, ед. изм."], "В т.ч.") then [#"Наименование работ, ед. изм."]  
                else if Text.Contains(#"Добавлен индекс"[#"Наименование работ, ед. изм."]{[Индекс]-1}, "В т.ч.") then "В т.ч. " & Text.Replace([#"Наименование работ, ед. изм."], Text.Split([#"Наименование работ, ед. изм."]," "){0}, Text.Lower(Text.Split([#"Наименование работ, ед. изм."]," "){0})) 
                else if Text.Contains(#"Добавлен индекс"[#"Наименование работ, ед. изм."]{[Индекс]-2}, "В т.ч.") then "В т.ч. " & Text.Replace([#"Наименование работ, ед. изм."], Text.Split([#"Наименование работ, ед. изм."]," "){0}, Text.Lower(Text.Split([#"Наименование работ, ед. изм."]," "){0}))
                else if Text.Contains(#"Добавлен индекс"[#"Наименование работ, ед. изм."]{[Индекс]-3}, "В т.ч.") then "В т.ч. " & Text.Replace([#"Наименование работ, ед. изм."], Text.Split([#"Наименование работ, ед. изм."]," "){0}, Text.Lower(Text.Split([#"Наименование работ, ед. изм."]," "){0}) )
                else if Text.Contains(#"Добавлен индекс"[#"Наименование работ, ед. изм."]{[Индекс]-4}, "В т.ч.") then "В т.ч. " & Text.Replace([#"Наименование работ, ед. изм."], Text.Split([#"Наименование работ, ед. изм."]," "){0}, Text.Lower(Text.Split([#"Наименование работ, ед. изм."]," "){0}))
                else  [#"Наименование работ, ед. изм."] otherwise [#"Наименование работ, ед. изм."])
Изменено: Николай Савенко - 16.10.2019 13:40:57
 
nnsavenko, а если после одной строки начинающейся с "В т.ч. " есть через одну еще строки, начинающиеся с этого же, то серия из четырех добавлений прерывается и начинается новая? Или все равно лепим повторно?
Вот горшок пустой, он предмет простой...
 
Да могут быть (особенно скрытые в Excel), но я решил эту проблему ранее, я удалил все пустые строки.
 
Николай Савенко, я не про пустые строки. А впрочем пофиг. Смотрите, так нужно?
Код
let
    Source = Excel.CurrentWorkbook(){[Name="ГР_Светлое__4"]}[Content],
    ChangedType = Table.TransformColumnTypes(Source,{{"Наименование работ, ед. изм.", type text}, {"План-сутки", type number}, {"Факт-сутки", type number}}),
    Set = [List = List.Buffer( ChangedType[#"Наименование работ, ед. изм."] ), Count = List.Count(List), Q = 4],
    Maker = List.Generate(
        () => [id = 0, check = if Text.StartsWith( Set[List]{id}, "В т.ч." ) then 0 else Set[Q], l = Set[List]{id}],
        each [id] < Set[Count],
        each [id = [id] + 1, check = if Text.StartsWith( Set[List]{id}, "В т.ч." ) then 0 else [check] + 1, l = if check > 0 and check <= Set[Q] then "В т.ч. " & Set[List]{id} else Set[List]{id}],
        each [l]),
    Out = Table.FromColumns( Table.ToColumns( ChangedType ) & {Maker}, Table.ColumnNames( ChangedType ) & {"новый"} )
in
    Out

З.Ы. и пока модераторы не расстроились, оформите в вашем первом посте кусок кода тегом CODE, это кнопка <..> на панели редактирования сообщения.
Если что, то источник мудроты по работе с генератором отсюда, ну и местные корифеи подкидывают иногда интересные решения, на них тоже учусь.
Оффтоп. Это что же реальное содержание в руде золотишка всего 1,5 г/т. И его еще выгодно добывать? Жесть.
Изменено: PooHkrd - 16.10.2019 13:29:37
Вот горшок пустой, он предмет простой...
 
Спасибо всем огромное.  
 
Цитата
PooHkrd написал:
его еще выгодно добывать?
не знаю как сейчас, а раньше для государства считалось рентабельным месторождение, у которого содержание золота было не менее 4,5 грамм. щас может быть такие (с низким содержанием золота) месторождения продают частным компаниям.
 
artyrH, совсем уж оффтоп, там вроде бы за счет добычи всякого сопутствующего, типа серебра, могут вырулить, ну и технологии аффинажа может удешевились. Но все равно. Раскурочить 3 тонны руды ради золота на небольшое колечко - это жесть.
Вот горшок пустой, он предмет простой...
 
Согласен, что частным компаниям. Но всё зависит от объёмов производства. Чем больше объёмы, тем меньше себестоимость.
 
Цитата
PooHkrd написал:
Раскурочить
раскурочить - это значит подорвать породу, перевезти глыбы на завод для дробления, измельчить глыбы в песок, нахимичить из песка золото. расходов на добычу не мало.
 
Решил свою задачу вот так, прошу прокомментировать, может есть лучше вариант решения:
Код
let
    Source = Excel.CurrentWorkbook(){[Name="ГР_Светлое__4"]}[Content],
    ChangedType = Table.TransformColumnTypes(Source,{{"Наименование работ, ед. изм.", type text}, {"План-сутки", type number}, {"Факт-сутки", type number}}),
    Set = [List = List.Buffer( ChangedType[#"Наименование работ, ед. изм."] ), Count = List.Count(List), Q = 4],
    Maker = List.Buffer (List.Generate(
        () => [id = 0, check = if Text.StartsWith( Set[List]{id}, "В т.ч." ) then 0 else Set[Q], l = Set[List]{id}],
            each [id] < Set[Count],
            each [id = [id] + 1, 
                        check = if Text.StartsWith( Set[List]{id}, "В т.ч." ) 
                                then 
                                    0 
                                else 
                                    [check] + 1, 
                l = if check > 0 and check <= Set[Q] 
                        then 
                            "В т.ч. " & Text.Replace( Set[List]{id}, Text.Split( Set[List]{id}," "){0}, Text.Lower(Text.Split(Set[List]{id}," "){0})) 
                        else 
                            Set[List]{id}],
            each [l])),
    t1 = List.Buffer (ChangedType[#"Наименование работ, ед. изм."]),
    //функция замены значений по списку
    TranslateFunction = (InputText)=> 
     let
       //функция замены значений
       DoRep = List.Generate(
                          ()=> [cnt=0, text=InputText], 
                          each [cnt]<=List.Count(t1), 
                          each [cnt=[cnt]+1, 
                                text=Text.Replace([text], t1{[cnt]}, Maker{[cnt]})], 
                          each [text]),
       GetLastValue = List.Last(DoRep)
     in
      GetLastValue,
    Output = Table.TransformColumns(ChangedType, {"Наименование работ, ед. изм.", each TranslateFunction(_), type text})
in
    Output
 
Зачем гонять списки два раза?
Просто подсуньте ему уже готовый вместо старого и делов то:
Код
let
    Source = Excel.CurrentWorkbook(){[Name="ГР_Светлое__4"]}[Content],
    ChangedType = Table.TransformColumnTypes(Source,{{"Наименование работ, ед. изм.", type text}, {"План-сутки", type number}, {"Факт-сутки", type number}}),
    Set = [List = List.Buffer( ChangedType[#"Наименование работ, ед. изм."] ), Count = List.Count(List), Q = 4],
    Maker = List.Generate(
        () => [id = 0, check = if Text.StartsWith( Set[List]{id}, "В т.ч." ) then 0 else Set[Q], l = Set[List]{id}],
        each [id] < Set[Count],
        each [id = [id] + 1, check = if Text.StartsWith( Set[List]{id}, "В т.ч." ) then 0 else [check] + 1, l = if check > 0 and check <= Set[Q] then "В т.ч. " & Set[List]{id} else Set[List]{id}],
        each [l]),
    Out = Table.FromColumns( {Maker} & List.Skip( Table.ToColumns( ChangedType ), 1 ), Table.ColumnNames( ChangedType ) )
in
    Out
Вот горшок пустой, он предмет простой...
 
Не правильно работает код, будем дальше разбираться, что не так делаю.
 
Спасибо, так просто :)
 
Николай Савенко, пример вы удалили - писал без проверки, может с синтаксисом чего попутал, но по сути, разбиваем таблицу на список столбцов, убираем первый столбец из списка, и вместо него цепляем новый столбец, потом собираем таблицу обратно.
Вот горшок пустой, он предмет простой...
 
Спасибо PooHkrd, как говорил товарищ Ленин: "Учиться, учиться и ещё раз учиться". Вы меня заставили по-другому взглянуть на Power query.
 
У меня получилось превратить в функцию:
Код
(ListColumn as list, N as number)=> 
    List.Generate(
        () => [id = 0, check = if Text.StartsWith( ListColumn{id}, "В т.ч." ) then 0 else N, l = ListColumn{id}],
        each [id] < List.Count (ListColumn),
        each [id = [id] + 1, check = if Text.StartsWith( ListColumn{id}, "В т.ч." ) then 0 else [check] + 1, l = if check > 0 and check <= N then "В т.ч. " & Text.Replace( ListColumn{id}, Text.Split( ListColumn{id}," "){0}, Text.Lower(Text.Split(ListColumn{id}," "){0}))  else ListColumn{id}],
        each [l])
 
Цитата
Николай Савенко написал:
Вы меня заставили
Не было такого! Сами, все сами. ;)
Цитата
Николай Савенко написал:
превратить в функцию
Это уж как вам хочется. В PQ за счет очень гибкой структуры языка и вывертов синтаксиса практически всегда имеется более одного варианта решения. Главное примерно представлять как ваш код отработает интерпретатор и выбирать самые экономные к ресурсам варианты.
Вот горшок пустой, он предмет простой...
Страницы: 1
Наверх