- Akciókamerák
- SSD kibeszélő
- Home server / házi szerver építése
- AMD Navi Radeon™ RX 9xxx sorozat
- Haladó fotósok digitális fényképei
- NVIDIA GeForce RTX 5080 / 5090 (GB203 / 202)
- NTFS, exFAT, FAT32 – Melyiket válaszd és miért?
- Mikrokontrollerek Arduino környezetben (programozás, építés, tippek)
- Léghűtés topik
- Asztrofotózás
-
PROHARDVER!
Új hozzászólás Aktív témák
-
Jim-Y
veterán
Ez kemény, átírtam a scriptet az alapján amit linkeltél:
$loc = get-location
$files = get-childitem -Path $loc -Recurse | where {$_.Length -gt 0}
$length = $files.length
$fileMap = @{}
$duplicates = @()
for($i=0;$i -lt $length;++$i){
$file = $files[$i]
$key = $file.Name +" "+ $file.Length +"byte"
if($fileMap.ContainsKey($key)){
$fileMap[$key] += $file.FullName
} else {
$fileMap[$key] = @($file.FullName)
}
}
foreach ($item in $fileMap.GetEnumerator()) {
if($item.Value.Length -gt 1){
$duplicates += $item.Name+":"
$duplicates += $item.Value
$duplicates += "`n"
}
}
$duplicates > fileMap.txtAmi eddig 45 percig futott most 15 mp volt
Ami eddig 22 mp volt az most 460 msMég leellenőrzöm, hogy ugyanazt az eredményt adja-e, de ránézésre igen
-
modder
aktív tag
Én valami ilyesmit próbálnék, nem ellenőriztem, hogy működik-e, de kíváncsi lennék mennyit fut
A $fileMap egy asszociatív tömb lesz, aminek az elemei listák az ugyanolyan nevű és méretű fájlok elérési útjáról. A végén csak azokat íratom ki, ahol ennek a listának a mérete nagyobb, mint 1, mert az azt jelenti, hogy több elérési út is tartozott ugyanahhoz a névhez és mérethez, tehát duplikált a fájl.
$loc = get-location
$files = get-childitem -Path $loc -Recurse | where {$_.Length -gt 0}
$length = $files.length
$fileMap = @{}
for($i=0;$i -lt $length;++$i){
$file = $files[$i]
$key = $file.Name + $file.Length
if($fileMap.ContainsKey($key)){
$fileMap[$key] += file.FullName
} else {
$fileMap[$key] = @(file.FullName)
}
}
foreach($duplicates in $fileMap.GetEnumerator()){
if($duplicates.length > 1){
Write-Host $duplicates.Name ( $duplicates.Value )
}
}
$fileMap > fileMap.txt -
Jim-Y
veterán
válasz
Jim Tonic #6418 üzenetére
Hát, pedig ezt írja ki:
Array assignment to [Village People - YMC ...] failed: Cannot convert value "Village People - YMCA.mp3" to type "System
.Int32". Error: "Nem megfelelő a bemeneti karakterlánc formátuma.".
At E:\_ATTILA\SCRIPTS\checkMusic.ps1:8 char:13
+ $multiples[ <<<< $key] = $value
+ CategoryInfo : InvalidOperation: (E:\_ATTILA\70\Village People - YMCA.mp3SObject) [], RuntimeExceptio
n
+ FullyQualifiedErrorId : ArrayAssignmentFailedkód:
$multiples = @()
foreach($elem in $files){
$key = $elem.Name.toString()
$value = $elem
$multiples[$key] = $value
} -
Jim-Y
veterán
válasz
Jim Tonic #6416 üzenetére
Mert mindenképp Int32-t szeretne kulcsnak
Példa:$files = get-childitem ... //fájlok beolvasása
$hashTable = @() //hashtable inicializálás
foreach($hash in $files){
//ezek közül egy se működött valamiért:(
$hashTable.$hash.Name = $hash
$hashTable[$hash.Name] = $hash
$hashTable["$hash.Name"] = $hash
$hashTable += {name=$hash.Name,value=$hash}
}több ötletem így hirtelen nem volt :/
-
Jim-Y
veterán
Közben próbálkoztam 1-2 dologgal
1: az eredeti
$loc = get-location
$files = get-childitem -Path $loc -Recurse | where {$_.Length -gt 0}
$length = $files.length
$multiples = @()
$rows = 0
$groups = 0
[int]$10n = $length*0.1
[int]$20n = $length*0.2
[int]$30n = $length*0.3
[int]$40n = $length*0.4
[int]$50n = $length*0.5
[int]$60n = $length*0.6
[int]$70n = $length*0.7
[int]$80n = $length*0.8
[int]$90n = $length*0.9
[int]$100n = $length
for($i=0;$i -lt $length;++$i){
$ismultiple = 0
$tempi = $files[$i]
switch($i)
{
$10n { write-host "10%" }
$20n { write-host "20%" }
$30n { write-host "30%" }
$40n { write-host "40%" }
$50n { write-host "50%" }
$60n { write-host "60%" }
$70n { write-host "70%" }
$80n { write-host "80%" }
$90n { write-host "90%" }
$100n { write-host "100%" }
}
if($multiples -contains $tempi.FullName){ } else {
for($j=$i+1;$j -lt $length;++$j){
$tempj = $files[$j]
if($tempj.Name -eq $tempi.Name -and $tempj.Length -eq $tempi.Length){
$multiples += $tempj.FullName
$rows++
$ismultiple = 1
}
}
if($ismultiple){
$multiples += $tempi.FullName
$rows++
$groups++
$multiples += "`n"
}
}
}
$multiples += "$loc folder has $length files, there are $groups files multiplied,`n and you could delete $($rows-$groups) files from the $rows multiplications!"
$multiples > multiples.txtEz a tesztmappán ~21-22mp-ig futott
2: nem tömbbe írós, hanem fileba:
Ebben a verzióban a $multiples tömb helyett amit a végén fájlba írok, egy fájlhozz appendelem szekvenciálisan a dolgokat
$multiples = @() -> New-Item multiples.txt -type file -force
$multiples += $files[$j].FullName ->
Add-Content multiples.txt -value $files[$j].FullName
stb..Ez a tesztmappán 1-2mp-el futott hosszabb ideig mint az első
3: hashmap
Sajnos nem sikerült olyan sszociatív tömböt csinálnom ahol a key-nek megette volna a fájl nevétÍgy egy .NET-es ArrayList-el próbálkoztam. Sajnos ez fut legtovább, a tesztmappán olyan 24mp-ig..
$loc = get-location
$hashTable = New-Object System.Collections.ArrayList(,(get-childitem -Path $loc -Recurse | where {$_.Length -gt 0}))
$duplications = New-Object System.Collections.ArrayList($null)
$rows = 0
$groups = 0
$length = $hashTable.Count
for($i=0;$i -lt $length;++$i){
$ism = 0
if($duplications.Contains($hashTable.Item($i).FullName)){ } else {
$temp = $hashTable.Item($i)
for($j=$i+1;$j -lt $length;++$j){
$tempj = $hashTable.Item($j)
if($tempj.Name -eq $temp.Name -and $tempj.Length -eq $temp.Length){
$duplications.Add($tempj.FullName)
$rows++
$ism = 1
}
}
if($ism) {
$rows++
$groups++
$duplications.Add($temp.FullName)
$duplications.Add("`n")
}
}
}
Write-Host "$length files, there are $groups files multiplied,`n and you could delete $($rows-$groups) files from the $rows multiplications!"
$duplications > multiples.txtMost véletlenül az egész partíció gyökerére futtattam le az első verziót, 10perc alatt csinált meg 10%-ot
-
Karma
félisten
Én sajnos nem eléggé, pedig ez most érdekes probléma
Találtam a PowerShellben egy tök hasznos funkciót: measure-command.
Ezzel pontosan ki tudod mérni, mi mennyi idő. -
Jim-Y
veterán
válasz
Sk8erPeter #6411 üzenetére
Nagyon ráérek, és ahogy ez lenni szokott, persze nem tanulással töltöm a feles időt
Ezzel kezdtem, így jutottam el a lentiig. -
Jim-Y
veterán
Magát a tömböt összeírni alig pár másodperc, nem az a hosszú, hanem ami a for ciklusban van, csináltam egy olyan kiiratást ami 10 százalékonként kiír a képernyőre, bár ez nem mutatja meg, hogy ténylegesen mi a sok idő...
Ami ötletem még van, az az, hogy ha egy fájlhoz összeszedi a duplikációkat, akkor azokat kitörli a tömbből, így a következő vizsgálandó fájlnál már annyival kevesebb elemet kell végignézni, bár ha kevés a duplikáció a mappában, akkor ez szinte semmit nem segítene. A másik ötletem, hogy az is lassú lehet amikor valamit hozzáadok a $multiples tömbhöz, mert elméletileg ilyenkor mindig készít egy másolatot az aktuális tömbről, legalábbis valami ilyesmit olvastam a neten, tehát lehet ezt a tömbhöz hozzáadok dolgot ki kéne cserélni valamire, például arra, hogy már az elején hozzon létre egy fájlt, majd utána csak appendoljon hozzá, hátha így gyorsabb lesz... majd mindjárt kipróbálom.
-
Karma
félisten
válasz
martonx #6407 üzenetére
Párhuzamos foreachre találtam valamit, szóval biztosan meg lehet kovácsolni.
De nem hiszem, hogy egy kétszeres szorzó megoldás lenne a négyzetes (vagy rosszabb, nem voltam jó algelből) algoritmusra. Oké, ötezer fájlt lenyom gyorsabban, tízezernél meg kezdődik elölről a tánc...
-
martonx
veterán
Szia!
Nem tudom powershell mennyire támogatja a párhuzamosságot, de mondjuk C#-ra átírva szépen és lazán ki tudod használni az összes processzormagot a gépben. Azaz a 2-3 perc futásidő, 2 magos gép esetében akár 1 percre is lemehet. Persze kérdés, hogy mennyi idő megy el a filerendszer használatával, mert azon a több mag nem segít.
-
modder
aktív tag
if($multiples -contains $files[$i].Name){ } -- Ahogy nő a $multiples tömb, egyre inkább több időt fog tölteni azzal, hogy a fájlnevet megtalálja benne, mert a -contains végignézi az egész tömböt. A duplikált fájlnevek tárolására használj inkább asszociatív tömböt, mert azt fájlnév szerint lehet címezni, és a szervezése Hash táblaszerű, tehát gyorsabb benne név alapján megtalálni egy elemet.
http://powershell.com/cs/blogs/tips/archive/2009/09/09/checking-whether-hash-table-contains-key.aspxfor($j=$i+1;$j -lt $length;++$j){
if($files[$j].Name -eq $elem.Name -and $files[$j].Length -eq $elem.Length){
$multiples += $files[$j].FullName
$ismultiple = 1
}
}
-- Itt a belső ciklusban szintén szekvenciálisan keresel végig a fájlnevek listáján, aminél átlagos keresési idő n/2. Jobb eredményt érsz el, ha először a fájlnevek listáját rendezed név szerint növekvő sorrendben, és egy ismert egyszerű kereső algoritmust használsz rá, pl. bináris keresés. Nem tudom, hogy erre van-e beépített szolgáltatása a Powershellnek, de lehet valaki már írt rá kódot a neten.Mivel gondolom egy egyszeri feladat volt, ezért már nem fogsz vele vacakolni, de van helye a fejlődésnek
-
-
Jim-Y
veterán
Sziasztok
PowerShellben csináltam egy olyan scriptet ami egy directoryban rekurzívan megnézi a duplikációkat, és a duplikált állományok nevét kigyűjti egy fájlba.
A problémám az, hogy az algoritmus amit használtam/írtam nagyon lassú. Ha ~2000 fájlt kell összehasonlítania az még viszonylag gyors 10,15mp, de 5500 állománnyal már percek óta szöszöl :S
megj: közben 2-3 perc múlva végzettAz ilyen rekurzív összehasonlítgatós dolgokat hogyan lenne célszerű megoldani?
Jelenleg a kódom:
$loc = get-location
$files = get-childitem -Path $loc -Recurse | where {$_.Length -gt 0}
$length = $files.length
$multiples = @()
for($i=0;$i -lt $length;++$i){
$ismultiple = 0
if($multiples -contains $files[$i].Name){ } else {
$elem = $files[$i]
for($j=$i+1;$j -lt $length;++$j){
if($files[$j].Name -eq $elem.Name -and $files[$j].Length -eq $elem.Length){
$multiples += $files[$j].FullName
$ismultiple = 1
}
}
if($ismultiple){
$multiples += $elem.FullName
$multiples += "`r`n`r`n"
}
}
}
$multiples > multiples.txtLátható, hogy először kigyűjtöm a fájlneveket egy tömbbe, majd az első rekordot keresem a fennmaradó elemek között, ha van duplikáció, akkor kiírom azokat a fájlba, és ugrok a második elemre.
Szinte biztos vagyok benne, hogy van ennél hatásosabb módszer, de már túl késő van ahhoz, hogy rájöjjek, hogy mi azmegj: haha, lehet csak azért szöszölt annyit, mert muter fél mappája duplikált, egy rahedli duplikációja van
Új hozzászólás Aktív témák
Hirdetés
● olvasd el a téma összefoglalót!
- Akciókamerák
- Átlépi végre az iPhone az 5000 mAh-t?
- SSD kibeszélő
- Audi, Cupra, Seat, Skoda, Volkswagen topik
- Home server / házi szerver építése
- AMD Navi Radeon™ RX 9xxx sorozat
- Parci: Milyen mosógépet vegyek?
- Haladó fotósok digitális fényképei
- NVIDIA GeForce RTX 5080 / 5090 (GB203 / 202)
- NTFS, exFAT, FAT32 – Melyiket válaszd és miért?
- További aktív témák...
- Telefon felvásárlás!! iPhone 16/iPhone 16 Plus/iPhone 16 Pro/iPhone 16 Pro Max
- ÚJ ÁRU, OLCSÓBB!!! Dell Precision Workstation 5550, 5560, 7510, 7520, 7550, 7720, i7, 6-11. gen.
- Bomba ár! Dell Latitude 5490 - i5-8GEN I 8GB I 256GB SSD I 14" HD I HDMI I Cam I W10 I Gari!
- LG 55C3 - 55" OLED evo - 4K 120Hz 1ms - NVIDIA G-Sync - FreeSync Premium - HDMI 2.1 - PS5 és Xbox!
- ÁRGARANCIA!Épített KomPhone i5 14600KF 32/64GB DDR5 RAM RTX 5070Ti 16GB GAMER PC termékbeszámítással
Állásajánlatok
Cég: Promenade Publishing House Kft.
Város: Budapest
Cég: CAMERA-PRO Hungary Kft
Város: Budapest