Збільшення кожного числа в рядку


11

Дано рядок, що містить десяткові числа:

teststring134this 123test string54 100

збільшуйте кожне число у цьому рядку на одне, щоб дати новий рядок

teststring135this 124test string55 101.

Рядок може бути наданий у вигляді:

  • аргумент командного рядка
  • STDIN
  • твердо кодовану змінну або аргумент функції

Покрийте всі можливі позиції для номера:

  • як префікс слова; 123test124test
  • як суфікс слова; test123test124
  • всередині слова; te123stte124st
  • поодинці test 123 testtest 124 test

Ось рішення, яке не займається гольфом в Python:

NUMBERS = '0123456789'

def increment(s):
    out = ''

    number = ''
    for c in s:
        if c in NUMBERS:
            number += c
        else:
            if number != '':
                out += str(int(number) + 1)
                number = ''
            out += c

    if number != '':
        out += str(int(number) + 1)
        number = ''

    return out


print "\"%s\"" % (increment('teststring134this 123test string54 100'))

Це code-golfпитання, виграє найкоротший код.


5
Цікавий факт: це може бути зроблено з 3 чистими регулярними виразами замін (без зворотних викликів) stackoverflow.com/questions/12941362 / ... (що не було б golfiest шляху , хоча)
Мартін Ендер

4
Ви вказали вхід, але не вихід. З вашого вводу специфікації я припускаю, що і STDOUT, і значення повернення нормально. Але чи можемо ми також зберегти результат у твердо кодованій змінній (так само, як ми можемо взяти з неї дані)?
Мартін Ендер

1
А що з носінням? Що відбувається з 999?
пухнастий


7
А як щодо негативних чисел? Що з числами з десятковою точкою? А як щодо цифр із десятковою комою і нічого перед цим (крім, можливо, знаку мінус)?
Пітер Тейлор

Відповіді:


23

Perl, 14 байт

s/\d+/$&+1/ge

Потрібен -pкомутатор, який я порахував як один байт.

Приклад виконання

$ perl -p <(echo 's/\d+/$&+1/ge') <<< 'teststring134this 123test string54 100'
teststring135this 124test string55 101

5
Дуже схожа на мою відповідь тут haha codegolf.stackexchange.com/a/37113/29438
hmatt1


11

Vim - 13 натискань клавіш

0qqqqq^Al@qq@q

Очікує, що введенням буде поточний рядок.

Або для кінцево багато цифр (наприклад, 999) в клавішах 8 + ceil (log (n)):

0qq^Alq999@q

Я не можу зробити цю роботу .... (я використовую vim 7.0.237)
Jerry Jeremiah

10

JavaScript (ES6) - 28

H=k=>k.replace(/\d+/g,k=>++k)

Запустити за допомогою H("test 123 234t").


1
Ви можете вийняти H=і просто мати анонімну функцію.
Mama Fun Roll

8

Перл, 23

Припускає, що введений рядок введення $_

s/\d+/@{[$&+1]}/g;print


6

C99 - 86 (GCC 4.9.0 та Visual C ++ 2013)

Редагувати: і GCC 4.9.0 (з -std = c99), і Visual C ++ 2013 успішно створюють (з попередженнями) один і той же код без включених. Я не знав, що ти можеш це зробити! Дякую за підказку.

Редагувати: Мені навіть не спадало на думку, що я повинен записувати його на екран, а не створювати рядок, а потім друкувати його. Це робить величезну зміну. Дякую Деннісе!

Для цього використовується жорстко закодований рядок, але вміст рядка не зараховується до загального (обчислюється = "").

main(i){for(char*q,*s="test123test999test-1test";i=strtol(s,&q,0),*s;q>s?printf("%d",i+1,s=q):putchar(*s++));}

В основному він проходить через рядок один символ одночасно, перевіряючи кожен, чи є це цілим числом. Якщо він є, то він збільшує ціле число і записує його на вихід, інакше він копіює поточний символ на вихід.

Це протікає з твердо кодованим рядком, оскільки він збільшує s.


1
Я впевнений, що ви можете позбутися деяких елементів include, і він все одно буде добре складатись з gcc.
Мартін Ендер

1
Чи буде це працювати з рядком, що містить напр. 99?
anatolyg

@ MartinBüttner: Так, але тоді це не було б дійсним C, а лише те, що трапляється працювати на gcc.
R .. GitHub ЗАСТАНОВИТИ ДІЯ

@R .. Це, як правило, дозволено на PPCG. Я бачив (і згодом це робив) досить часто, не скаржившись.
Мартін Ендер

Так, і це загальне моє око. Мова повинна бути вказана як "GCC" або "C на [конкретна арка / тощо., Хаки, можливо, працюють на]" або подібні, а не C, якщо це не дійсно C. :-)
R .. GitHub STOP ДОПОМОГАТИ ДВІ

5

J (20)

Очікує, що вхід буде збережений у змінній a.

'\d+'>:&.".rxapply a

Тест:

   a=:'teststring134this 123test string54 100'
   '\d+'>:&.".rxapply a
teststring135this 124test string55 101

5

(f?) lex (39)

Файл inc.l:

%%
[0-9]+ printf("%d",atoi(yytext)+1);

Збірка:

$ flex inc.l
$ gcc lex.yy.c -o inc -lfl

Виконати:

$ echo 'teststring134this 123test string54 100' | ./inc
teststring135this 124test string55 101

$ i='(-: 2 empty bottles of beer :-)'
$ tty=$(tty)
$ for n in {2..5} ; do i=$(./inc<<<$i|tee $tty) ; done
(-: 3 empty bottles of beer :-)
(-: 4 empty bottles of beer :-)
(-: 5 empty bottles of beer :-)
(-: 6 empty bottles of beer :-)

Я не перевіряв цього з оригіналом lex. Коментарі вітаються.


1
Ви можете відмовитись від трейлінгу, %%оскільки це не код користувача: flex.sourceforge.net/manual/…
Josh,

Гей ... так! Я спробував, але не затримуючи новий рядок, і це не вдалося ... тоді я не намагався додати остаточний рядок ... ;-) ... дурна помилка!

3

Emacs - 20 символів

C-M-% [0-9]+ RET \,(1+ \#0) RET !

Потрібен текст для обробки, щоб він був присутній у поточному буфері. Тут я порахував CM-% як один символ, оскільки його можна ввести одним натисканням клавіші, утримуючи три модифікатори.


3

GNU sed, 304 (включаючи 1 прапор -r)

Я закрив це питання як можливий дублікат, але це, мабуть, суперечить тому, що цю відповідь неможливо змінити, щоб там працювати. Але далеко не найдовша відповідь.

Натхненний цим прикладом з документації sed , хоча для роботи з декількома числами в рядку потрібна була деяка робота:

:d
s/9([^0-9]+|$)/_\1/g
td
s/8(_*)([^0-9]+|$)/9\1\2/g
s/7(_*)([^0-9]+|$)/8\1\2/g
s/6(_*)([^0-9]+|$)/7\1\2/g
s/5(_*)([^0-9]+|$)/6\1\2/g
s/4(_*)([^0-9]+|$)/5\1\2/g
s/3(_*)([^0-9]+|$)/4\1\2/g
s/2(_*)([^0-9]+|$)/3\1\2/g
s/1(_*)([^0-9]+|$)/2\1\2/g
s/0(_*)([^0-9]+|$)/1\1\2/g
s/(^|[^0-9_]+)(_+)/\11\2/g
y/_/0/

Вихід:

$ for s in "teststring134this 123test string54 100" "123test" "test123" "te123st" "test 123 test" ; do echo "$s" | sed -rf incr.sed ; done
teststring135this 124test string55 101
124test
test124
te124st
test 124 test
$ 

Зверніть увагу, що це тимчасово вставляє _символи, тому це може призвести до неправильних результатів, якщо вони є _у вхідному потоці. Як пом’якшення цього, ми можемо замінити _сценарій sed на деякий недрукувальний символ (наприклад, ASCII 0x07 BEL), і припустимо, що вхідний потік містить лише ASCII, що можна друкувати. Це, здається, працює добре, коли я його тестую.



2

Луа - 68 символів

d='(%D-)'for k,i,j in s:gmatch(d..'(%d+)'..d)do io.write(k,i+1,j)end

Очікує, що вхід буде збережено в s.


2

CJam, 67 58 53 48 31 персонажів

Це питання як найгірше питання для CJam. Ніяких регулярних виразів, не збігання шаблонів, не виняток. Але ось ми ідемо (#YOLO)

Sl+_A,sNerN%\[_A,s-Ner~]:)]zs1>

Цей розділяє рядок на групу лише алфавітів і просто цифр. Збільшити кожну цифру і зшити назад два масиви, беручи по одному елементу по одному.


Попереднє рішення:

L_l{:Ci57-zA<:RC*+:N\R!N*NNW?i):NL?+RLC?@R*}/NL?

Спробуйте його онлайн тут

Як це працює:

Основна ідея полягає в тому, щоб зберігати символ окремо в рядку, якщо він є цифрою, і скидати нарощене значення до остаточного рядка, як тільки ми отримаємо нецифровий символ.

L_                                               "Push two empty strings to stack,"
                                                 "first representing the final string"
                                                 "and second, the current ongoing number";
  l{                                       }/    "Run this block for each character of input string";
    :Ci                                          "Store the character to C and convert to"
                                                 "its ASCII equivalent integer";
       57-zA<:R                                  "Subtract 57 from the integer and compare"
                                                 "its absolute value with 10. Numeric character"
                                                 "would result to true here. Store the result in R";
               C*+:N                             "Take either 0 or 1 characters from C based"
                                                 "on value of R, add it to the second string"
                                                 "from first step. Also store the value in N";
                    \                            "Switch the strings. Now the string containing"
                                                 "the final result string is at top of stack";
                     R!N*                        "If the character was not a digit and N contains a number in it";
                         NNW?i):NL?+             "Convert N to number and increment it."
                                                 "If N is blank, take 0 instead. Put the final"
                                                 "value back in N and add it to the final result string";
                                    RLC?         "If the character was not a digit, push it to stack";
                                        @R*      "Put the ongoing numeric string back to top of stack";
                                             NL? "This is to handle the case when the last number"
                                                 "is not followed by a string, so stack will"
                                                 "have a string at top. Push the value of N to stack in that case";

1

Кобра - 88

do(s='')=RegularExpressions.Regex.replace(s,'\d+',do(m as Match)='[int.parse("[m]")+1]')

1

C # - 178 169 157 символів

Це передбачає, що числа типу 999 дозволяється переповнювати до 000, а це - +, E не є частиною числа.

class T{static void Main(){var a="".ToCharArray();for(int b=1,c,i=a.Length;i-->0;b=48>c|c>57?7:b>0?c>56?a[i]='0':++a[i]*0:b)c=a[i];System.Console.Write(a);}}

Краще читаема форма:

class T
{
    static void Main()
    {
        var a="7teststring134this 123test string59 100".ToCharArray();

        for (int b=3, c, i=a.Length; i-->0;
            b=48>c|c>57
                ?7
                :b>2
                    ?c>56?a[i]='0':++a[i]*0
                    :b
        ) c=a[i];

        System.Console.Write(a);
        System.Console.ReadKey();
    }
}

Я тут новий, ніколи раніше не пробував код гольфу, просто спробував :)

Цікаво, чи є у когось ідеї, щоб зробити його ще коротшим ...

Для участі в C # було б непогано, якби ми могли опустити всі необхідні рамки навколо фактичного коду - тоді це буде лише 82 символи, і це без виклику жодних потужних системних функцій.


Те саме з покажчиками (182 символів):

class T
{
    unsafe static void Main()
    {
        char[] a="7teststring134this 123test string59 100".ToCharArray();

        int b=3;
        fixed (char* s=&a[0])
            for (var p=s+a.Length; p-->s; )
                b=*p<48|*p>57
                    ?7
                    :b>2
                        ?*p>56?*p='0':++*p*0
                        :b;

        System.Console.Write(a);
        System.Console.ReadKey();
    }
}

Тепер, не переповнюючи, це правильно обробляє корпус 999 (223 символів):

class T
{
    static void Main()
    {
        var s=new System.Text.StringBuilder("9999teststring134this 123test string99 100");

        for (int b=3, c, i=s.Length; i-->0; )
        {
            c=s[i];
            b=48>c|c>57
                ?b>8?8:7
                :b>2
                    ?c>56?c-(s[i]='0'):++s[i]*0
                    :b;
            if (b>8&i<1|b==8) s.Insert(i+9-b, '1');
        }

        System.Console.Write(s);
        System.Console.ReadKey();
    }
}

Ще один інший, старший, він читає зі стандартного вводу та використовує рекурсію:

namespace System {
    using C=Console;
    class T {
        class t {
            byte b=1;
            string s="";
            void R() {
                var c=C.Read();
                if (c>31) {
                    R();
                    if (48>c|c>57) b=1;
                    else if (b==1) c=c==57?48:++c*b--;
                    s=(char)c+s;
                }
            }
            public t() {
                R();
                C.Write(s);
            }
        }
        static void Main() {
            new t();
            C.ReadKey();
        }
    }
}

Примітка: Console.ReadKey();і сам рядок не слід рахувати.

Я вдосконалював це вже багато разів, дивіться коментарі. Більше вдосконалень, я б сказав :) Є ще пробачення за тривалість, але я думаю, що різні версії досить цікаві, щоб зберегти їх ...


ні, позбавлення від "оточення" не дозволяється. Я вважаю, що у вашому другому коді після if(c==57)того, як ви могли написати c--;замість того c=48;, що і з потрійним оператором. існує безліч хитрощів з гольфу. можливо, варто відвідати codegolf.stackexchange.com/questions/2203/tips-for-golfing-in-c
гордий haskeller

Дякую, я нічого не знаю про гольф :) все, що ви бачите тут, було придумано мною ;-) 57-1 - це не 48. Тож я не розумію.
maf-soft

На жаль :-) :-) :-) :-)
гордий haskeller

Я насправді не знаю С # добре, але, мабуть, ви можете використовувати якогось оператора, щоб ... ? ... : c++*b--
зв'язати

btw вибачте за те, що надіслали вам поради C замість C # tips: codegolf.stackexchange.com/questions/173/…
гордий haskeller


0

PHP - 91 байт

<?$i=fgets(STDIN);for($n=0;$n<strlen($i);$n++)if(is_numeric($i[$n]))$i[$n]=$i[$n]+1;echo$i;

Я не хотів використовувати регулярні вирази. PHP не здатний безпосередньо збільшити зміщення рядка, тому мені потрібно було додати кілька байтів на крок збільшення. Цей сценарій з одним рядком запам'ятовує мені дуже темний вік сценаріїв PHP ...


Я вже спостерігав, що в цьому питанні ви вимагаєте збільшити кількість результатів послідовності алгаризмів. Ця відповідь невірна. Але я дійсно вважаю, що оп повинен додати більше деталей про те, що він хоче.
Олександр Телес


0

sed і bash - 40 (включаючи виклик і труби)

$ cat << EOF |sed 's/[0-9]\+/$((\0+1))/g;s/^/echo /'|bash
teststring134this 123test string54 100
123test
test123
te123st
test 123 test
EOF

Виходи:

teststring135this 124test string55 101
124test
test124
te124st
test 124 test

Я спробував цей тестовий рядок: 42;rm -rf /він спрацював уперше.
Денніс

2
Ви можете змінити \0на &(-1 символ), $((…))на $[…](-2 символи), s/^/echo /на iecho \\(-2 символи), щоб скоротити поточний код. Однак краще спочатку виправити помилку, згадану @Dennis. (Він писав : «Він працював в перший раз» для задоволення і , як натяк на питання На насправді ваш код не на вході , що містить. ;, #, `…`, $(…)І , можливо , інші спеціальні символи теж.)
manatwork

Довільне виконання коду - це особливість :-)
mgjk

Можливо, немає способу пройти цей маршрут без якихось обмежень для введення та збереження коду невеликим. Природа рішення полягає в тому, щоб перекласти вхід і використовувати інтерпретатор, щоб зробити математику, оскільки sed не може цього зробити. Як тільки користувальницьке введення потрапляє на інтерпретатора, випускний сигнал стає гайким. За винятком попереднього прикладу sed, sed не може займатися математикою.
mgjk

Дещо коротше: eval echo `sed 's/[0-9]\+/$[&+1]/g'`- все-таки є проблема введення коду, хоча, відповідно до моєї відповіді на інше подібне питання codegolf.stackexchange.com/a/37145/11259
Digital Trauma

0

Java 7, 119 байт

void c(String s){for(String x:s.split("(?=[^\\d]+)|(?<=[^\\d]+)"))System.out.print(x.matches("\\d+")?new Long(x)+1:x);}

Якщо вимога - це програма, а не просто функція, то це 149 байт:

class M{public static void main(String[]a){for(String x:a[0].split("(?=[^\\d]+)|(?<=[^\\d]+)"))System.out.print(x.matches("\\d+")?new Long(x)+1:x);}}

Невикористаний і тестовий код:

Спробуйте тут.

class M{
  static void c(String s){
    for(String x : s.split("(?=[^\\d]+)|(?<=[^\\d]+)")){
      System.out.print(x.matches("\\d+")
                        ? new Long(x) + 1
                        : x);
    }
  }

  public static void main(String[] a){
    c("123test");
    System.out.println();
    c("test123");
    System.out.println();
    c("te123st");
    System.out.println();
    c("test 123 test");
    System.out.println();
    c("7teststring134this 123test string59 100");
  }
}

Вихід:

124test
test124
te124st
test 124 test
8teststring135this 124test string60 101

0

Гема, 14 символів

<D>=@add{$1;1}

Проба зразка:

bash-4.3$ gema '<D>=@add{$1;1}' <<< 'teststring134this 123test string54 100'
teststring135this 124test string55 101

0

DASH , 16 байт (неконкурентоспроможний)

rstr[R"\d+""g"+1

Це повертає функцію / часткове додаток.

Використання:

rstr[R"\d+""g"+1]"test 123 234t"

Пояснення

rstr[          #. replace any parts of the input
  R "\d+" "g"  #. matching /\d+/g
  +1           #. with its incremented form
]

Це відповідь неконкурентна?
Денніс

ой рип :( я якось подумав, що це питання щодо каталогу.
Mama Fun Roll

0

CJam, 18 байт

q_A,s-_:(:`ers~]:)

Спробуйте тут.

Пояснення

q         e# Read input.
_A,s-     e# Duplicate and remove digits.
_         e# Duplicate.
:(:`      e# Decrement and get the string representation of each character.
er        e# Map the characters to the decremented string representation.
s~        e# Flatten to string and evaluate.
]:)       e# Wrap in an array and increment each element.

0

R, 83 байти

Пізно на вечірку. Припускає, що вхід зберігається в змінній x. Це, мабуть, не потрібно використовувати regmatchesдля вирішення цього питання, але я не міг з'ясувати векторизовані заміни без жодних зовнішніх пакетів.

paste0(el(r(x,m<-gregexpr("\\d+",x),T)),c(as.numeric(el(r(x,m)))+1,""),collapse="")

Необережений і пояснив

r=regmatches                                        # Alias for regmatch
y=r(x<-scan(,""),m<-gregexpr("\\d+",x))             # return match digits
i=r(x,m,T)                                          # return inverted match (non-digits)
paste0(el(i),c(as.numeric(el(y))+1,""),collapse="") # join digits+1 and non-digits, element-wise

Приклад виведення

input: 
"teststring135this 124test string55 101"

output:
[1] "teststring136this 125test string56 102"

0

C # (Visual C # Interactive Compiler) з опцією командного рядка /u:System.Text.RegularExpressions.Regex;System.Int32, 40 байт

Replace(n,"\\d+",m=>Parse(m.Value)+1+"")

Очікує, що вхід буде в змінній з назвою n.

Спробуйте в Інтернеті!


2
Недійсний, не можна очікувати введення змінної
лише для ASCII

@ ascii-тільки Це питання, мабуть, прямо дозволяє це "хоча особисто я б спробував дотримуватися сьогоднішніх стандартів введення
Джо Кінг,

Зачекайте: / ew це запитання
лише для ASCII
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.