Форум программистов, компьютерный форум, киберфорум
PowerShell
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.89/9: Рейтинг темы: голосов - 9, средняя оценка - 4.89
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566

Использование Linq в PowerShell

07.03.2024, 22:02. Показов 3884. Ответов 37
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Всем привет! Если кто в курсе, подскажите, пожалуйста, возможно ли получить разницу 2-х пользовательских объектов с помощью linq.enumerable, используя except? Заранее благодарен!
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
07.03.2024, 22:02
Ответы с готовыми решениями:

Использование возможностей WPF в PowerShell
хочу выполнить вот такую команду для дальнейшего использования возможностей WPF в powershell import-module wpk мне выдает ошибку...

Использование скрипта powerShell в C#
Есть скрипт на powershell, как его встроить прямо в код в c#? В скрипте имеются как двойные ковычки (с которыми еще можно справиться), так...

Использование PowerShell в .Net Framework
Хочу использовать power shell. В документации на msdn написано, что для использования нужно подключить System.Management.Automation.dll....

37
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 13:47  [ТС]
Студворк — интернет-сервис помощи студентам
iNNOKENTIY21, хорошо, даю подробное описание боевой задачи. Есть 2 списка, одинаковых по структуре элементов, но разных по объёму. Списки я представил в виде csv-файлов (во вложении). Надо из table_1 вычесть table_2, сравнивая объекты списков по атрибуту league_guid
Вложения
Тип файла: zip data.zip (207.0 Кб, 13 просмотров)
0
2807 / 505 / 121
Регистрация: 26.09.2020
Сообщений: 959
Записей в блоге: 5
10.03.2024, 14:24
Karen87, я бы так сделал
PowerShell
1
2
3
4
5
6
7
$t1 = Import-Csv .\table_1.csv
$t2 = Import-Csv .\table_2.csv
 
$r = $t1 | Where-Object { $t2.league_guid -NotContains $_.league_guid }
 
'{0} - {1} = {2}' -f $t1.Count, $t2.Count, ($t1.Count - $t2.Count)
'records left: {0}' -f $r.Count
0
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 14:30  [ТС]
iNNOKENTIY21, на данный момент примерно так и работает, но хочется реализовать с помощью [linq.enumerable] опять же с заделом на задачи, в которых объемы элементов будут измеряться сотнями тысяч

Добавлено через 2 минуты
Основной вопрос:
Почему долго отрабатывает:
PowerShell
1
$array = [Linq.Enumerable]::ToArray($compare)
0
 Аватар для alhaos
1934 / 549 / 155
Регистрация: 20.02.2019
Сообщений: 2,675
Записей в блоге: 77
10.03.2024, 14:41
Karen87, А какой результат бы вас устроил?

PowerShell
1
2
3
4
5
6
7
8
$m = Measure-Command {
    $coll1 = Import-Csv C:\tmp\001\table_1.csv
    $coll2 = Import-Csv C:\tmp\001\table_2.csv
    $coll3 = (Compare-Object $coll1 $coll2 | Where-Object SideIndicator -eq "<=").InputObject
    write-host $coll3.Count
}
 
$m.Microseconds
Code
1
2
5874
542
0
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 14:49  [ТС]
alhaos, результат, который дает Ваше решение конечно отличный, но темой обсуждения является использование библиотеки linq. Почему скорость работы с ее использованием в сотни раз ниже, чем, например, Вашего решения? Например, join в linq отрабатывает на "ура" при использовании тех же объектов. Что не так с except?
0
 Аватар для alhaos
1934 / 549 / 155
Регистрация: 20.02.2019
Сообщений: 2,675
Записей в блоге: 77
10.03.2024, 14:54
При значительном объеме данных, имеет смысл доверить это дело СУБД, хотя я где то видел как человек выпил пятишку воды палочками для еды, тоже наверное имеет смысл...

Добавлено через 1 минуту
Karen87, Ну да проблема есть, она стабильно провоцируется, надо бы найти ее решение...
0
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 14:54  [ТС]
alhaos, в курсе про СУБД, а так же в курсе, что linq предназначен для оптимизации производительности при работе с большими объемами данных, о чем Вы, видимо, не в курсе
0
 Аватар для alhaos
1934 / 549 / 155
Регистрация: 20.02.2019
Сообщений: 2,675
Записей в блоге: 77
10.03.2024, 15:03
Karen87, да, я не особо в курсе про оптимизацию работы с данными в Linq, я немного в курсе как это делать в СУБД, и я думаю если это бы можно было делать эффективнее то это бы уже было в Oracle, MSSql и других СУБД.

Добавлено через 1 минуту
еще есть вариант Linq'ом обратиться к СУБД )))
0
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 15:04  [ТС]
alhaos, как реализовать задачу в MSSQL я знаю, так же через инструкцию EXCEPT, но мне нужна реализация в linq, если она возможна в контексте powershell, поэтому я здесь
0
2807 / 505 / 121
Регистрация: 26.09.2020
Сообщений: 959
Записей в блоге: 5
10.03.2024, 15:08
Лучший ответ Сообщение было отмечено Karen87 как решение

Решение

Karen87, с linq тоже быстро
PowerShell
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
$t1 = Import-Csv .\table_1.csv
$t2 = Import-Csv .\table_2.csv
 
class ComparerCustomObject : System.Collections.Generic.IEqualityComparer[pscustomobject] {
    [bool] Equals([pscustomobject] $o1, [pscustomobject] $o2) {
        return $o1.league_guid -eq $o2.league_guid
    }
 
    [int] GetHashCode([pscustomobject] $obj) {
        if ($null -eq $obj) { return 0 } else { return $obj.league_guid.GetHashCode() }
    }
}
 
$compare = [linq.enumerable]::Except(
    [System.Collections.Generic.List[pscustomobject]] $t1,
    [System.Collections.Generic.List[pscustomobject]] $t2,
    [ComparerCustomObject]::new()
)
 
$array = [linq.enumerable]::ToArray($compare)
$array.Count
1
 Аватар для alhaos
1934 / 549 / 155
Регистрация: 20.02.2019
Сообщений: 2,675
Записей в блоге: 77
10.03.2024, 16:12
PowerShell
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
$coll1 = Import-Csv .\table_1.csv
$coll2 = Import-Csv .\table_2.csv
 
$coll3 = @()
 
$m = Measure-Command {
 
    :out
    for ($i = 0; $i -lt $coll1.Count; $i++) {
        for ($j = 0; $j -lt $coll2.Count; $j++) {
            if (
                $coll1[$i].league_guid -eq $coll2[$j].league_guid
            ) {
                continue out
            }
        }
        $coll3 += $coll1[$i]
    }
}
 
"Count       : {0}" -f $coll3.Count
"Microseconds: {0}" -f $m.Microseconds
Code
1
2
Count       : 5874
Microseconds: 55
PowerShell
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
$t1 = Import-Csv .\table_1.csv
$t2 = Import-Csv .\table_2.csv
 
class ComparerCustomObject : System.Collections.Generic.IEqualityComparer[pscustomobject] {
    [bool] Equals([pscustomobject] $o1, [pscustomobject] $o2) {
        return $o1.league_guid -eq $o2.league_guid
    }
 
    [int] GetHashCode([pscustomobject] $obj) {
        if ($null -eq $obj) { return 0 } else { return $obj.league_guid.GetHashCode() }
    }
}
 
$m = Measure-Command {
$compare = [linq.enumerable]::Except(
    [System.Collections.Generic.List[pscustomobject]] $t1,
    [System.Collections.Generic.List[pscustomobject]] $t2,
    [ComparerCustomObject]::new()
)
 
$array = [linq.enumerable]::ToArray($compare)
 
}
 
"Count       : {0}" -f $array.Count
"Microseconds: {0}" -f $m.Microseconds
Code
1
2
Count       : 5874
Microseconds: 344
Может на существенно больших данных это ведет себя лучше...
0
2807 / 505 / 121
Регистрация: 26.09.2020
Сообщений: 959
Записей в блоге: 5
10.03.2024, 16:27
alhaos, а в TotalMilliseconds?
0
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 16:34  [ТС]
iNNOKENTIY21, наконец-то заработало, спасибо) Последний вопрос, а как реализовать проверку по двум и более атрибутам в аспекте метода GetHashCode при описании класса ComparerCustomObject? Я так понимаю по аналогии с первым предложенным Вами вариантом?
0
 Аватар для alhaos
1934 / 549 / 155
Регистрация: 20.02.2019
Сообщений: 2,675
Записей в блоге: 77
10.03.2024, 16:45
iNNOKENTIY21, блин тупанул, да два порядка в пользу линк
0
2807 / 505 / 121
Регистрация: 26.09.2020
Сообщений: 959
Записей в блоге: 5
10.03.2024, 16:53
Цитата Сообщение от Karen87 Посмотреть сообщение
с первым предложенным Вами вариантом?
ага.
1
 Аватар для alhaos
1934 / 549 / 155
Регистрация: 20.02.2019
Сообщений: 2,675
Записей в блоге: 77
10.03.2024, 17:14
iNNOKENTIY21,
PowerShell
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
$t1 = Import-Csv .\table_1.csv
$t2 = Import-Csv .\table_2.csv
 
class ComparerCustomObject : System.Collections.Generic.IEqualityComparer[pscustomobject] {
    [bool] Equals([pscustomobject] $o1, [pscustomobject] $o2) {
        return $o1.league_guid -eq $o2.league_guid
    }
 
    [int] GetHashCode([pscustomobject] $obj) {
        if ($null -eq $obj) { return 0 } else { return $obj.league_guid.GetHashCode() }
    }
}
 
$m = Measure-Command {
$compare = [linq.enumerable]::Except(
    [System.Collections.Generic.List[pscustomobject]] $t1,
    [System.Collections.Generic.List[pscustomobject]] $t2,
    [ComparerCustomObject]::new()
)
 
$array = [linq.enumerable]::ToArray($compare)
 
}
 
"Count       : {0}" -f $array.Count
"Microseconds: {0}" -f $m.TotalMicroseconds
Code
1
2
Count       : 5874
Microseconds: 86222,7
но оправдания ради...
если делать упор на эффективность...

Go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
package main
 
import (
    "encoding/csv"
    "fmt"
    "os"
    "time"
)
 
func main() {
 
    f1, _ := os.Open(`C:\tmp\001\table_1.csv`)
    f2, _ := os.Open(`C:\tmp\001\table_2.csv`)
 
    r1 := csv.NewReader(f1)
    r1.Comment = '#'
    r1.FieldsPerRecord = 4
    r1.LazyQuotes = true
    r2 := csv.NewReader(f2)
    r2.Comment = '#'
    r2.FieldsPerRecord = 4
    r2.LazyQuotes = true
 
    t1, err := r1.ReadAll()
    if err != nil {
        panic(err)
    }
    t2, err := r2.ReadAll()
    if err != nil {
        panic(err)
    }
    t3 := make([][]string, 0, len(t1))
 
    t := time.Now()
out:
    for _, t1Row := range t1 {
        for _, t2Row := range t2 {
            if t1Row[0] == t2Row[0] {
                continue out
            }
        }
        t3 = append(t3, t1Row)
    }
 
    fmt.Printf("Count       : %d\n", len(t3))
    fmt.Printf("Microseconds: %d\n", time.Now().Sub(t).Microseconds())
}
Code
1
2
Count       : 5875
Microseconds: 2619
0
3449 / 1110 / 494
Регистрация: 29.05.2016
Сообщений: 4,566
10.03.2024, 17:46  [ТС]
Цитата Сообщение от alhaos Посмотреть сообщение
но оправдания ради...
если делать упор на эффективность...
Честнее было бы сравнить, например, C++ и Go или C# и Go. PowerShell, ИМХО, всё-таки является API с возможностью заюзать .Net
1
Нарушитель
7164 / 2333 / 353
Регистрация: 10.12.2013
Сообщений: 8,072
21.05.2025, 15:02
зацепился взором.

PowerShell
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
$list1 = [Collections.ArrayList]::new()
 
1..6000 |% {$rnd=[random]::new()} {[void]$list1.add([pscustomobject]@{id=$rnd.next(1,2000000000);name="test$_";age=$rnd.next(1,100)})}
 
$list2 = $list1.clone(); [void]$list1.Add([pscustomobject]@{id=0;name="testSUPER";age=999})
 
measure-command {
 
$list1|Export-Csv -Path __list1.csv
$list2|Export-Csv -Path __list2.csv
 
@"
.sep ","
.import __list1.csv list1
.import __list2.csv list2
.headers on
.mode csv
.output __result.csv
select * from list1 except select * from list2;
"@ | sqlite3 :memory:
 
$result = import-csv __result.csv
}
 
$result

чудовищно неоптимально, но тем не менее:

6000 x 6000 objects - 170 миллисекунд
60000 x 60000 objects - 1.5 секунды

включая операции:
- список в файл сохранить ( export-csv )
- список в файл сохранить ( export-csv )
- sqlite3 запустить
- sqlite читает и разбирает файл csv
- sqlite читает и разбирает файл csv
- sqlite выполняет запрос и сохраняет в файл csv
- прочитать и разобрать результат из csv ( import-csv )

Если возню с файлами убрать и заправлять в sqlite непосредственно, будет быстрее раз в 5; 35 миллисек


другой вопрос - зачем связываться с pscustomobject, если можно сделать класс с hash-массивом
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
21.05.2025, 15:02

Использование Linq запросов
задание Создать проект Windows Form. Описать структуру согласно заданию. Считать данные в коллекцию структур из текстового файла (не...

Использование Linq в .NET 4.0
Пытался перевести код с шарпа на пабс.нет Int min = list.Min(x=&gt;x.ToString().Length); Грубо говоря, вычисление минимальной длины...

Использование ИЛИ в LINQ
Ситуация простая, но не могу понять почему формируется не правильный запрос. Запрос должен быть таким, он выводит например 20 строк ...

Задача на использование LINQ
Дано целое число K (&gt; 0) и последовательность непустых строк A. Строки последовательности содержат только цифры и заглавные буквы...

Использование Krypton компонентов и linq
Решил приукрасить проект с данными компонентами. Но столкнулся с проблемой, не могу использовать пространство System.Linq... Его просто...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
38
Ответ Создать тему
Новые блоги и статьи
Скрипты Tampermonkey для CyberForum, ChatGPT, Claude и пр.
Jin X 06.09.2026
Скрипты Tampermonkey для CyberForum, ChatGPT, Claude и пр. Работая с форумом и нейросетями в браузере часто хочется что-то подкорректировать или добавить какого-то функционала. Ниже прикреплён. . .
Программа опроса у.з. расходомера SLS-720F
Argus19 02.09.2026
Программа опроса у. з. расходомера SLS-720F Программа опрашивает один раз в минуту три ультразвуковых расходомера SLS-720F через интерфейс RS-485 по протоколу Modbus RTU. Опрашиваются регистры. . .
Hyper-V: Компьютер должен поддерживать доверенный платформенный модуль 2.0.
Maks 31.08.2026
При установке Windows 11 на виртуальную машину Hyper-V 2-го поколения вылезла такая ошибка: Решение: в параметрах виртуальной машины, в разделе "Безопасность" (Security) активировать флаг. . .
Архитектура биовида Стива в Майнкрафте: Зачем бонобо кубический каннибализм
anaschu 30.08.2026
Кубический Вагинокапитализм в Minecraft: Математический инвариант ОДУ и рок Стивов-бонобо Главная задача разработанной «Модели Всего» — наглядно продемонстрировать наличие системной «судьбы». . .
Оттачиваю умение писать js программы.
russiannick 30.08.2026
Проектом выходного дня стало написание Книги шифров Виженера. Итогом стала версия 200, синий туман. Синий туман назван так, потому что замораживает текст под собой. Нажатие синих кнопок управляют. . .
мат медиц модель 30. презентация проекта
anaschu 27.08.2026
хоп хоп хоп хидахоп, а я кладую))
Как у меня протекала болезнь
zorxor 27.08.2026
Здравствуйте, друзья! Эта запись блога предназначена именно для вас - для моих дорогих друзей, которые знали меня лично. Чтобы ответить на вопрос - а что же со мной произошло на самом деле? Я учился. . .
Нашел вот забавное видео о измерениях. Лучшее что я видел на эту тему
kumehtar 26.08.2026
ILETXiw9bMQ Основная суть и тезисы по измерениям: 0D (Нулевое измерение): точка, не имеющая длины, ширины, высоты или объема. Объект не может перемещаться в 0D. 1D (Первое измерение):. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru