Имя пользователя:
Пароль:
 | Правила  

Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » Скриптовые языки администрирования Windows » Любой язык - [решено] Удалить первый байт в файле

Ответить
Настройки темы
Любой язык - [решено] Удалить первый байт в файле

Аватара для m0nkrus

Старожил


Сообщения: 150
Благодарности: 16

Профиль | Сайт | Отправить PM | Цитировать


Приветствую!

Задача следующая: нужно удалить первый байт в файле. Этот процесс нужно автоматизировать, поскольку этот байт мне нужно удалить более чем в сотне файлов. Так что если на выходе получится скрипт, который опрашивает директорию с субдиректориями, и все находящиеся в них файлы смещает на один байт вверх, уничтожая этот байт, было бы идеально. Если имена конечных файлов слегка изменятся (например, к имени прибавится цифра 1), это не принципиально.

Отправлено: 21:26, 30-04-2021

 

Аватара для YuS_2

Crazy


Contributor


Сообщения: 1235
Благодарности: 518

Профиль | Отправить PM | Цитировать


Цитата m0nkrus:
Только и успеваю увидеть красный цвет надписи. »
Скрипт можно выполнить непосредственно в консоли, тогда она не будет закрыта и ошибку можно будет и прочитать, и скопировать.

-------
scio me nihil scire. Ѫ

Это сообщение посчитали полезным следующие участники:

Отправлено: 08:47, 01-05-2021 | #11



Для отключения данного рекламного блока вам необходимо зарегистрироваться или войти с учетной записью социальной сети.

Если же вы забыли свой пароль на форуме, то воспользуйтесь данной ссылкой для восстановления пароля.


Аватара для m0nkrus

Старожил


Сообщения: 150
Благодарности: 16

Профиль | Сайт | Отправить PM | Цитировать


YuS_2, не знал про это. Привык, что в cmd в консоль перенести готовый сценарий нельзя...

Ваш скрипт на семерке выдавал такую ошибку:
Код: Выделить весь код
Get-ChildItem : Не удается найти параметр, соответствующий имени параметра "file".
строка:1 знак:16
+ dir $root -file <<<<  -rec|%{
    + CategoryInfo          : InvalidArgument: (:) [Get-ChildItem], ParameterBindingException
    + FullyQualifiedErrorId : NamedParameterNotFound,Microsoft.PowerShell.Commands.GetChildItemCommand

Get-ChildItem : Не удается найти параметр, соответствующий имени параметра "file".
строка:6 знак:16
+ dir $root -file <<<<  -rec|%{
    + CategoryInfo          : InvalidArgument: (:) [Get-ChildItem], ParameterBindingException
    + FullyQualifiedErrorId : NamedParameterNotFound,Microsoft.PowerShell.Commands.GetChildItemCommand

Отправлено: 08:51, 01-05-2021 | #12


Аватара для DJ Mogarych

fascinating rhythm


Moderator


Сообщения: 6705
Благодарности: 1576

Профиль | Отправить PM | Цитировать


Судя по всему, у вас старый Powershell. Проверяется командой
Код: Выделить весь код
host
Его можно обновить до версии 5.1
https://docs.microsoft.com/ru-ru/pow...powershell-7.1

-------
Powershell 7.x | Powershell 5.1 | ffmpeg (docs)

Это сообщение посчитали полезным следующие участники:

Отправлено: 08:54, 01-05-2021 | #13


Аватара для YuS_2

Crazy


Contributor


Сообщения: 1235
Благодарности: 518

Профиль | Отправить PM | Цитировать


Цитата m0nkrus:
Не удается найти параметр, соответствующий имени параметра "file". »
Это значит, что версия powershell 2.0, её надо обновить до 5.1, либо вместо параметра -file, в первом командлете, добавить в конвейер:
Код: Выделить весь код
|?{!$_.PSIsContainer}
т.е. в целом, код выглядеть будет так:
Код: Выделить весь код
$root = 'd:\test'
dir $root -rec|?{!$_.PSIsContainer}|%{
    $bytes = [io.file]::readallbytes($_.fullname)
    [io.file]::writeallbytes($_.fullname, $bytes[1..($bytes.count-1)])
}

-------
scio me nihil scire. Ѫ

Это сообщение посчитали полезным следующие участники:

Отправлено: 08:57, 01-05-2021 | #14


Аватара для m0nkrus

Старожил


Сообщения: 150
Благодарности: 16

Профиль | Сайт | Отправить PM | Цитировать


DJ Mogarych, YuS_2, совершенно верно. Версия 2.0. Обновил до 5.1 и скрипты заработали корректно на семерке. Спасибо!

Отправлено: 09:06, 01-05-2021 | #15


Аватара для YuS_2

Crazy


Contributor


Сообщения: 1235
Благодарности: 518

Профиль | Отправить PM | Цитировать


Цитата m0nkrus:
Задача не разовая, увы. »
Ну тогда, как-то так:
Код: Выделить весь код
param (
	[string]$folder = '.\TEST'
)
function RW-Stream {
	param (
		[Parameter(ValueFromPipeline)]
		[ValidateNotNullOrEmpty()]
		$filein,
		$fileout = 'tmp.tmp'
	)
	begin {
		new-variable -name block -val 524288
		$buf = new-object byte[] ($block)
	}
	process {
		#measure-command{
		$reader = [io.streamreader]::new($filein.fullname)
		$writer = [io.streamwriter]::new($fileout)
		$reader.basestream.position = 1
		while ($reader.basestream.position -lt $reader.basestream.length){
			$cnt = $reader.basestream.read($buf,0,$block)
			$writer.basestream.write($buf,0,$cnt)
		}
		$reader.dispose();$writer.dispose()
		$reader.close();$writer.close()
		mi $fileout $filein.fullname -force
		#}
	}
}

dir $folder -file -rec|rw-stream
- скрипт принимает в качестве параметра наименование корневого каталога (можно указать абсолютный путь).
Корневой каталог сканируется рекурсивно. Целевые файлы заменяют исходные, то бишь копии нигде не создаются, поэтому применять осторожно, если исходные файлы потребуются в неизменном виде.

Файл ~250Мб, обрабатывается:
TotalSeconds : 7,5637454

Файл ~4,2Гб, обрабатывается:
TotalSeconds : 145,7682588

-------
scio me nihil scire. Ѫ


Последний раз редактировалось YuS_2, 04-11-2021 в 20:43.

Это сообщение посчитали полезным следующие участники:

Отправлено: 18:32, 04-11-2021 | #16


Аватара для m0nkrus

Старожил


Сообщения: 150
Благодарности: 16

Профиль | Сайт | Отправить PM | Цитировать


YuS_2, рекурсивно получаю ошибку:
Цитата:
You cannot call a method on a null-valued expression.
At E:\Design&Graphics\Unpack\onebyte.ps1:22 char:4
+ $cnt = $reader.basestream.read($buf,0,$block)
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : InvokeMethodOnNull
Единственное, что менял в скрипте, это ".\TEST" заменил на "c:\test"

Последний раз редактировалось m0nkrus, 04-11-2021 в 20:01.


Отправлено: 19:52, 04-11-2021 | #17


Аватара для YuS_2

Crazy


Contributor


Сообщения: 1235
Благодарности: 518

Профиль | Отправить PM | Цитировать


Цитата m0nkrus:
рекурсивно получаю ошибку »
Всё время забываю проверить на powershell v5.1, тестирую на pwsh 7.2, а у них есть различия...
В общем, там строчку надо удалить было
Код: Выделить весь код
$filein = gi $filein
- она была нужна из расчета на то, чтобы в функцию можно было вместо объекта передавать строку с путем... но в варианте с командлетом Get-ChildItem (dir), она не критична и не нужна...
- в общем, тут в скрипте я уже исправил

-------
scio me nihil scire. Ѫ

Это сообщение посчитали полезным следующие участники:

Отправлено: 20:49, 04-11-2021 | #18


Аватара для m0nkrus

Старожил


Сообщения: 150
Благодарности: 16

Профиль | Сайт | Отправить PM | Цитировать


YuS_2, честно говоря, я слегка в шоке! По скорости обработки этот скрипт по сравнению с прошлым, это как небо и земля. Спасибо огромное!

P.S. А можно на всякий случай еще скрипт со строчкой "$filein = gi $filein"? Когда-нибудь перейду на десятку, а там уже версия PowerShell будет актуальной.

Последний раз редактировалось m0nkrus, 04-11-2021 в 21:29.


Отправлено: 21:18, 04-11-2021 | #19


Аватара для YuS_2

Crazy


Contributor


Сообщения: 1235
Благодарности: 518

Профиль | Отправить PM | Цитировать


Цитата m0nkrus:
Когда-нибудь перейду на десятку, а там уже версия PowerShell будет актуальной. »
Дык, pwsh v7.2 можно установить и на семерку (он вполне портабелен)... и они будут параллельно работать, не мешая друг другу...

Цитата m0nkrus:
на всякий случай еще скрипт со строчкой "$filein = gi $filein"? »
Эта строка была, вот перед этой:
Код: Выделить весь код
$reader = [io.streamreader]::new($filein.fullname)
Там можно условие добавить с проверкой версии powershell и не удалять её
Но, по сути, эта строка работала бы в случае вот такого вызова функции
Код: Выделить весь код
rw-stream "d:\folder\file.ext"
то бишь, без неё вполне можно обойтись, просто в параметр вызова не давать строку, а сразу объект, например так:
Код: Выделить весь код
$obj = gi "d:\folder\file.ext"
rw-stream $obj
и всё будет функционировать без этой строки...

-------
scio me nihil scire. Ѫ


Отправлено: 21:49, 04-11-2021 | #20



Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » Скриптовые языки администрирования Windows » Любой язык - [решено] Удалить первый байт в файле

Участник сейчас на форуме Участник сейчас на форуме Участник вне форума Участник вне форума Автор темы Автор темы Шапка темы Сообщение прикреплено

Похожие темы
Название темы Автор Информация о форуме Ответов Последнее сообщение
Любой язык - Удалить все метаданные в файле shadowbat Скриптовые языки администрирования Windows 0 03-03-2020 15:49
CMD/BAT - [решено] Удалить первый символ из строки Darkar25 Скриптовые языки администрирования Windows 4 06-04-2019 11:59
CMD/BAT - [решено] удалить файл от 0 до 100 байт Freddy1984 Скриптовые языки администрирования Windows 15 14-06-2017 16:05
Любой язык - [решено] Удалить последний байт в файле pzh2393 Скриптовые языки администрирования Windows 10 06-12-2014 19:28
[решено] Изменить байт в файле по смещению. semiono AutoIt 2 29-08-2010 22:57




 
Переход