Разрыв кода Applescript при удалении конечных пробелов - PullRequest
0 голосов
/ 09 июля 2019

То, что должно быть простым фрагментом кода для удаления последнего символа из строки, похоже, ломается без видимой причины (для меня, во всяком случае).

Я пытаюсь создать простой скрипт для устранения проблем с синхронизацией файлов OneDrive, когда у них есть лишние пробелы вокруг имен файлов и расширений.

Возвращаясь к AppleScript через очень долгое время и, кажется, все забыл, просто нужно понять, почему то, что должно быть простым, кажется, сбило меня с толку ... будьте нежны со мной.

on stripSpaces(thisText)
    local newText
    local pos
    local tempText

    set newText to thisText

    set tempText to ""

    repeat while tempText ≠ newText
        set tempText to newText

        --remove spaces before extension name
        set pos to the offset of ". " in newText

        if pos > 0 then
            set newText to ((characters 1 thru pos of newText) as text) & (characters (pos + 2) thru end of newText) as text
        end if

        --remove spaces before extension
        set pos to the offset of " ." in newText

        if pos > 0 then
            set newText to ((characters 1 thru (pos - 1) of newText) as text) & (characters (pos + 1) thru end of newText) as text
        end if

        --remove leading spaces
        if character 1 of newText = " " then
            set newText to characters 2 thru end of newText as text
        end if

        ---BROKEN SECTION

        --remove trailing spaces
        if (last character of newText) = " " then
            set newText to (characters 1 thru (end of newText) - 1) as text
        end if
    end repeat

    return newText
end stripSpaces

log stripSpaces("   spa     .          nish  . txt  ")

ошибка "Не могу закончить \" спа. Ниш. текст \"." номер -1728 от последней точки вставки "spa. nish. txt"

Ответы [ 3 ]

1 голос
/ 14 июля 2019

Я немного опаздываю. Тед Ригли смотрит на мяч, совершенно справедливо замечая, что самым лучшим и эффективным решением является способ text item delimiters.Я откладываю ему заслугу за то, что он предоставил, на мой взгляд, наиболее подходящий из предложенных ответов, к которому это, по сути, всего лишь продолжение, чтобы проиллюстрировать, что можно достичь идентичных результатов с помощью гораздо более компактного двухстрочного обработчика:

to removeAllWhitespace from input as text
    set text item delimiters to {pi, space, tab, linefeed, return}
    return the input's text items as text
end removeAllWhitespace

Я также позволил себе убрать все (традиционные) пробельные символы, кроме space, то есть tab, а также символы новой строки.Вероятно, вы можете сделать вывод, как удалить эти опции, если хотите.

Для вызова обработчика:

removeAllWhitespace from "   spa     .          nish  . txt  "

, который выдает: "spa.nish.txt"


А?Pi ...?

Короче: Выберите что-нибудь случайное, что не является текстом и вряд ли появится в имени файла.Если сомневаетесь: используйте pi ^ pi.

Подробно: Не слишком увлекайтесь тем, что pi: использование piв приведенном выше списке разделителей не имеет значения как само по себе количество, и единственная функция, которую он выполняет, - это нестроковый объект, который разрешает все разделители всписок, который будет удален из имени файла, который будет включать в себя любые вхождения себя в строковой форме, т.е. "3.14159265359".При условии, что эта последовательность символов не появляется в имени файла, pi, вероятно, является хорошим выбором, чтобы служить этим «фиктивным разделителем».В противном случае ключ должен поменять pi на любое другое нестроковое значение.Скажи ... pi + 1?Я часто использую null, missing value или случайное число.Но, если вы когда-нибудь обнаружите, что не можете сами создать номер или придумать его самостоятельно, просто используйте pi ^ pi.

0 голосов
/ 09 июля 2019

Прямой ответ на ваш вопрос: вы не должны использовать «конец» в этом контексте, но используйте «-1» для обозначения последнего символа, «-2» для обозначения второго до последнего символа и т. Д.результат будет выглядеть примерно так:

on stripSpaces(thisText)
    local newText
    local pos
    local tempText

    set newText to thisText

    set tempText to ""

    repeat while tempText ≠ newText
        set tempText to newText

        --remove spaces before extension name
        set pos to the offset of ". " in newText

        if pos > 0 then
            set newText to ((characters 1 thru pos of newText) as text) & (characters (pos + 2) thru -1 of newText) as text
        end if

        --remove spaces before extension
        set pos to the offset of " ." in newText

        if pos > 0 then
            set newText to ((characters 1 thru (pos - 1) of newText) as text) & (characters (pos + 1) thru -1 of newText) as text
        end if

        --remove leading spaces
        if character 1 of newText = " " then
            set newText to characters 2 thru -1 of newText as text
        end if

        ---BROKEN SECTION

        --remove trailing spaces
        if (last character of newText) = " " then
            set newText to (characters 1 thru -2 of newText) as text
        end if
    end repeat

    return newText
end stripSpaces

log stripSpaces("   spa     .          nish  . txt  ")

Однако, если ваша цель - просто убрать пробелы, вы можете сделать это намного эффективнее, используя разделители текстовых элементов:

on stripSpaces(thisText)
    set tid to my text item delimiters
    set my text item delimiters to " "  -- break text at spaces
    set textParts to text items of thisText
    set my text item delimiters to ""  -- recombine text without spaces
    set strippedText to textParts as text
    set my text item delimiters to tid
    return strippedText
end stripSpaces

log stripSpaces("   spa     .          nish  . txt  ")
0 голосов
/ 09 июля 2019

Гораздо проще получить текстовые диапазоны с text 1 thru -1 of newText, где -1 - последний символ.Это позволяет избежать также всех as text принуждений.

on stripSpaces(thisText)
    local newText
    local pos
    local tempText

    set newText to thisText

    set tempText to ""

    repeat while tempText ≠ newText
        set tempText to newText

        --remove spaces before extension name
        set pos to the offset of ". " in newText

        if pos > 0 then
            set newText to text 1 thru pos of newText & text (pos + 2) thru -1 of newText
        end if

        --remove spaces before extension
        set pos to the offset of " ." in newText

        if pos > 0 then
            set newText to text 1 thru (pos - 1) of newText & text (pos + 1) thru -1 of newText
        end if

        --remove leading spaces
        if first character of newText = space then
            set newText to text 2 thru -1 of newText
        end if

        --remove trailing spaces
        if last character of newText = space then
            set newText to text 1 thru -2 of newText
        end if
    end repeat

    return newText
end stripSpaces

log stripSpaces("   spa     .          nish  . txt  ")

С небольшой помощью AppleScriptObjC весь обработчик может быть уменьшен до двух строк

use AppleScript version "2.4" -- Yosemite (10.10) or later
use framework "Foundation"

on stripSpaces(thisText)
    set nsText to current application's NSString's stringWithString:thisText
    return (nsText's stringByReplacingOccurrencesOfString:" " withString:"") as text
end stripSpaces

log stripSpaces("   spa     .          nish  . txt  ")
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...