Самые высокие или самые низкие вхождения?

13

Вызов:

Входы:

  • Строка, содержащая печатный ASCII (исключая пробелы, табуляции и новые строки)
  • Логическое

Выход:

Части Строки делятся на четыре группы:

  • Строчные буквы
  • Заглавные буквы
  • Digits
  • Другой

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

Например:

Входные данные: "Just_A_Test!"
содержит:
- 3 заглавные буквы: JAT
- 6 строчных букв: ustest
- 0 цифр
- 3 другие:__!

Это будут результаты для trueили false:

true:   " ust    est "

// digits have the lowest occurrence (none), so everything is replaced with a space
false:  "            "

(Примечание. Вы можете игнорировать конечные пробелы, поэтому выходные данные также могут быть " ust est"и ""соответственно.)

Правила вызова:

  • Ввод никогда не будет пустым или будет содержать пробелы и будет состоять только из печатного ASCII в диапазоне 33-126или '!'сквозном '~'.
  • Вы можете принимать входные данные и / или выходные данные как массив символов или список, если хотите.
  • † Допускаются любые два согласованных и различных значения для логического значения: true/ false; 1/ 0; 'H'/ 'L'; "highest"/ "lowest"; и т. д. Обратите внимание, что эти различные значения должны использоваться (в некоторой степени) как логическое значение! Поэтому нельзя вводить две полные программы, одна из которых дает правильный результат, trueа другая - для false, а затем иметь только фактический код <run input with parameter>. Я добавил соответствующую новую лазейку по умолчанию, хотя она все еще может использовать много тонких настроек в отношении определений.
  • Если вхождение двух или более групп совпадает, мы выводим все эти вхождения.
  • Необходимые завершающие пробелы являются необязательными, и одна конечная новая строка также необязательна. Необходимые пробелы обязательны. И любые другие ведущие пробелы или новые строки не допускаются.

Основные правила:

  • Это , поэтому выигрывает самый короткий ответ в байтах.
    Не позволяйте языкам кода-гольфа отговаривать вас от публикации ответов на языках, не относящихся к кодексу. Попробуйте найти как можно более короткий ответ для «любого» языка программирования.
  • К вашему ответу применяются стандартные правила , поэтому вы можете использовать STDIN / STDOUT, функции / метод с соответствующими параметрами, полные программы. Ваш звонок.
  • По умолчанию лазейки запрещены.
  • Если возможно, добавьте ссылку с тестом для вашего кода.
  • Также, пожалуйста, добавьте объяснение, если это необходимо.

Тестовые случаи:

Inputs:                              Output:

"Just_A_Test!", true                 " ust    est "     (or " ust    est")
"Just_A_Test!", false                "            "     (or "")
"Aa1!Bb2@Cc3#Dd4$", either           "Aa1!Bb2@Cc3#Dd4$"
"H@$h!n9_!$_fun?", true              " @$ !  _!$_   ?"
"H@$h!n9_!$_fun?", false             "H     9        "  (or "H     9")
"A", true                            "A"
"A", false                           " "                (or "")
"H.ngm.n", true                      "  ngm n"
"H.ngm.n", false                     "       "          (or "")
"H.ngm4n", false                     "H.   4 "          (or "H.   4")
Кевин Круйссен
источник
Допустимо ли выводить наибольшее / наименьшее количество как отдельные записи? Например, для тестового примера «хэширование - это весело» можно "H "и " 9 "вместо (с соответствующими пробелами) выводить "H 9"?
AdmBorkBork
@AdmBorkBork Я не понимаю, что вы имеете в виду; как Hи 9являются частью «меньше всего».
Эрик Outgolfer
Может ли логическое входное значение быть "max"/ "min", которое затем используется как Math[b]ссылка Math.maxили Math.min?
Джастин Маринер
@JustinMariner Вы знаете .. Я передумал об этом извините. Я думаю, это для JS? Я думаю, что многие языки программирования могут использовать что-то вроде этого, поэтому слишком многие из существующих ответов должны быть изменены. Извините, вам придется держать b?"max":"min"в своем ответе .. Это тонкая грань, я думаю, может быть, я должен просто использовать значение truey / falsey в следующий раз ..
Кевин Круйссен

Ответы:

3

Шелуха , 27 26 24 22 байта

-2 байта благодаря Zgarb

-2 байта благодаря Лео

Берет ' 'как Falseи 'a'какTrue (В Husk, пробел в Fasly и все остальные символы являются правдой)

Fż▲→ġ#¬Ö#≡⁰Ṫḟë½D±o¬□m;

Попробуйте онлайн!

Как это работает?

Fż▲→ġ#¬Ö#≡⁰Ṫḟë½D±o¬□m;   Function, takes a character c and a string S as arguments
                    m;   Wrap each character in S into it's own string
             ë           List of four functions returning booleans:
              ½D±o¬      Lower case?,Upper case?,Digit?,Not alphanumeric?
           Ṫḟ            Outer product with find†
       Ö#≡⁰              Sort on how many characters have the same Truthyness as c
    ġ#¬                  Group strings with equal numbers of spaces
   →                     Take the last group
Fż▲                      Squash it all into one list

это функция, которая принимает предикат pи список Lи возвращает первый элемент, Lкоторый удовлетворяет p. Если ни один элемент не удовлетворяет, pвозвращается аргумент по умолчанию. В этом случае ' '. Применяя к одной символьной строке, мы по существу говоримif p c then c else ' ' .

Есть функция , которая принимает функцию fи два списка L1, L2. Возвращает таблицу fприменений по всем парам L1и L2. В этом случае fэто ,L1 наш список из 4 -х функций, и L2список из одной строки символов.

После того, как Ṫḟу нас есть список строк, где каждая строка является результатом замены символов, которые не удовлетворяют одному из правил,' ' .

NB. В более новых версиях Husk ġ#¬Ö#≡⁰может быть заменено k#≡⁰на 3 байта!

H.PWiz
источник
Из любопытства: почему ' 'и 'a'? Может быть, я понимаю это лучше, когда добавляется объяснение, потому что я не могу читать Хаска. ;)
Кевин Круйссен
Ницца! Вот 24 использования байтов .
Згарб
@ Zgarb Спасибо! Я не очень понял, что Mmmделал сам :)
H.PWiz
К сожалению, это не очень помогает в игре в гольф, но S`?' может быть проще, чем?IK'
Лев
Я стараюсь избегать использования I, иногда это заставляет переводчика работать вечно. Это также кажется расточительным.
H.PWiz
7

Желе , 31 байт

ØṖḟØBṭØBUs26¤f€³Lİ⁴¡$ÐṀFf
¹⁶Ç?€

Попробуйте онлайн!

Логические значения - это 2и 1(или любая другая положительная четная / нечетная пара), которые представляютTrue и Falseсоответственно. Я постараюсь добавить объяснение после дальнейшей игры в гольф.

Спасибо caird coinheringaahing за сохранение 2 байта и Линн за сохранение 4 байта! Благодаря одному из приемов Эрика , который вдохновил меня сэкономить 4 байта!

Как это устроено

Обратите внимание, что это объяснение 35-байтовой версии. Новый делает примерно то же самое (но немного подправил Линн), поэтому я не буду его менять.

ØBUs26f€³µ³ḟØBW,µẎLİ⁴¡$ÐṀF - Niladic helper link.
ØB                         - String of base digits: '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ
                             abcdefghijklmnopqrstuvwxyz'. 
  U                        - Reverse.
   s26                     - Chop into sublists of length 26, preserving shorter
                             trailing substrings.
      f€³                  - For each, keep the common characters with the input.
            ØB             - Base digits.
          ³ḟ               - Get the signs in the input. Filter the characters of the
                             input that aren't alphanumeric.
              W,µẎ         - Concatenate (wrap, two element list, tighten).
                       ÐṀ  - Keep the elements with maximal link value.
                  L        - Length.
                    ⁴¡     - Do N times, where N is the second input.
                   İ       - Inverse. Computes 1 ÷ Length. 2 maps to the length itself,
                             because 1 ÷ (1 ÷ Length) = length; 1 yields
                             (1 ÷ Length), swapping the maximal numbers with minimal ones.
                         F - Flatten.

¹⁶e¢$?€ - Main link.
      € - For each character.
   e¢?  - If it is contained by the last link (called niladically), then:
¹       - Identity, the character itself, else:
 ⁶      - A space.
Мистер Xcoder
источник
40 байт
Caird Coneheringaahing
@cairdcoinheringaahing Спасибо! :) Я хотел сыграть в эту партию с тех пор, как опубликовал ответ, но не мог понять, почему он не сработал ... У меня был посторонний µD:
Мистер Xcoder,
31 байт : генерировать классы как ØṖḟØBṭØBUs26¤, а затем проверять членство с fи Çвместо e¢$.
Линн
5

Python 2 , 166 158 байт

t=lambda c:('@'<c<'[','`'<c<'{','/'<c<':',1-c.isalnum())
def f(s,b):x=map(sum,zip(*map(t,s)));print''.join([' ',c][x[t(c).index(1)]==sorted(x)[-b]]for c in s)

Попробуйте онлайн!

TFeld
источник
158 байт
г-н Xcoder
@ Mr.Xcoder Спасибо; Только что получил это :)
TFeld
5

R , 193 186 179 158 байт

-7 байт благодаря NofP и его предложению cbind

Использование -6 байтов outer, переключение -1 байта [^a-zA-Z0-9]с[[:punct:]]

-21 байт, спасибо MickyT за указание списка символов

function(S,B){y=outer(c("[a-z]","[A-Z]","\\d","[[:punct:]]"),S,Vectorize(grepl))
S[!colSums(y[(s=rowSums(y))=="if"(B,max,min)(s),,drop=F])]=" "
cat(S,sep='')}

Проверьте все контрольные примеры

Принимает 1/Tкак truey ( max) и 0/Fкак falsey ( min) и принимаетS список отдельных символов.

Попробуйте онлайн!

В моей исходной версии (с предложениями NofP) матрица yстроится путем оценки grepl(regex, S)каждого из них regex, а затем объединяет их вместе в виде столбцов матрицы. Это приводит к многочисленным вызовам grepl, но, как Sэто было установлено, казалось, что нужно что-то еще сделать. Как я уже отметил:

Есть потенциально более короткие подходы; mapply, например:

y=mapply(grepl,c("[a-z]","[A-Z]","\\d","[^a-zA-Z0-9]"),list(S))

к сожалению, это не упростит в качестве матрицы в 1-символьном примере "A" .

Я использовал outerвместо mapply, который всегда возвращает массив (матрица в данном случае), и был вынужденVectorize grepl , что на самом деле является просто mapplyоберткой вокруг него.

Я также обнаружил предопределенную группу символов, [:punct:]которая соответствует знакам пунктуации (не пробелы, не алфавитно-цифровые).

Giuseppe
источник
1
Если вы замените матрицу cbind, вы можете уменьшить ее до 186 байтов: y = cbind (g ("[az]", S), g ("[AZ]", S), g ("\\ d", S), г («[^ a-zA-Z0-9]», S))
NofP
@ Ноф, очень мило. Кроме того, вы можете заключить код в кавычки (`), чтобы он отображался like this. :)
Джузеппе
Правила S=el(strsplit(G,""))
гласят,
@ MickyT ах, я не заметил этого, спасибо.
Джузеппе
4

Шелуха , 31 29 28 байт

SMS?' `ṁ§foSM≠?▲▼⁰M#Kë½D±o¬□

Использует 0 для минимального и 1 для максимального количества символов. Попробуйте онлайн!

объяснение

Списки функций это круто.

SMS?' `ṁ§foSM≠?▲▼⁰M#Kë½D±o¬□  Inputs are bit B and string S.
                     ë        Make a list L of the four functions
                      ½       is-lowercase-letter,
                       D      is-uppercase-letter,
                        ±     is-digit, and
                         o¬□  not is-alphanumeric.
                  M#          For each of them, take number of matches in S,
              ?▲▼⁰            take maximum or minimum depending on B,
          oSM≠                and mark those entries that are not equal to it.
        §f          K         Remove from L the functions that correspond to marked entries, call the result L2.
                              These functions test whether a character should be replaced by a space.
SM                            Do this for each character C in S:
      `ṁ                      Apply each function in L2 to C and sum the results.
  S?'                         If the result is positive, return space, otherwise return C.
Zgarb
источник
4

Python 2 , 140 байт

g=lambda x:x.isalnum()-~(x>'Z')*x.isalpha()
def f(s,m):k=map(g,s).count;print''.join([' ',c][k(g(c))==sorted(map(k,range(4)))[m]]for c in s)

Попробуйте онлайн!

Джонатан Фрех сохранил байт. Благодарность!

Самый высокий m=-1, самый низкий m=0.

Линн
источник
1
Я думаю, что вы можете сохранить байт, заменив +x.isalpha()*-~(x>'Z')на -~(x>'Z')*x.isalpha().
Джонатан Фрех
3

Java (OpenJDK 8) , 448 439 432 362 361 354 352 348 343 320 байт

s->b->{int w[]=new int[4],m=0,n=-1>>>1,l;s.chars().forEach(c->{if(c>96&c<123)w[0]++;else if(c>64&c<91)w[1]++;else if(c>47&c<58)w[2]++;else++w[3];});for(int W:w){m=W>m?W:m;n=W<n?W:n;}l=m-n;m=b?m:n;return l<1?s:s.replaceAll("["+(w[0]!=m?"a-z":"")+(w[1]!=m?"A-Z":"")+(w[2]!=m?"\\d]":"]")+(w[3]!=m?"|[^a-zA-Z0-9]":"")," ");}

Попробуйте онлайн!

Роберто Грэм
источник
366 байт
Кевин Круйссен,
Вы можете удалить +in \\|+$для дополнительного -1 байта.
Кевин Круйссен
Вы можете сохранить еще три байта, изменив последнюю часть на String r=(w[0]!=m?"[a-z]|":"")+(w[1]!=m?"[A-Z]|":"")+(w[2]!=m?"[0-9]|":"")+(w[3]!=m?"[^a-zA-Z0-9]|":"");return r.isEmpty()?s:s.replaceAll(r.replaceAll(".$","")," ");}.
Кевин Круйссен,
Ох, и n=s.length()может быть n=-1>>>1за дополнительную -4.
Кевин Круйссен
О, еще одна маленькая вещь для гольфа: [0-9]->\\d
Кевин Круйссен
3

Руби , 118 116 байт

Берет 0(низший) или-1 (самый высокий) для своего второго аргумента.

-2 байта благодаря Линн.

->s,t{s.gsub(/./){|c|[/\d/,/[a-z]/,/[A-Z]/,/[^\da-z]/i].group_by{|x|s.scan(x).size}.sort[t][1].any?{|x|x=~c}?c:" "}}

Попробуйте онлайн!

Ungolfed

->s,t{
  s.gsub(/./) {|c|
    [ /\d/,
      /[a-z]/,
      /[A-Z]/,
      /[^\da-z]/i
    ]
    .group_by {|x| s.scan(x).size }
    .sort[t][1]
    .any? {|x| x =~ c } ? c : " "
  }
}
Иордания
источник
Очень классный ответ! Вы можете использовать -1в качестве «самого высокого» значения и заменить minmax[t]на sort[t].
Линн
3

Python 2, 190 183 174 173 байта

Спасибо Джонатану Фречу за сокращение

from re import*
def f(i,c):
 q='[a-z]','[A-Z]','\d','[\W_]';l=[len(set(finditer(p,i)))for p in q]
 for j,k in enumerate(l):
	if k-eval(c):i=compile(q[j]).sub(' ',i)
 print i

Это принимает строки 'max(l)'и 'min(l)'как правда, и ложь. (Я не думаю, что это нарушает правила ...?) Это длиннее, чем два других ответа на Python, но отличается, поэтому я решил опубликовать его. Я не большой игрок в гольф, поэтому я думаю, что это можно улучшить, но все, что я пробовал, не сработало.

Попробуйте онлайн!

dylnan
источник
Здравствуйте и добро пожаловать на сайт! Когда я пытаюсь запустить это, я получаю ошибки, и я не совсем уверен, почему. Одной из причин может быть то , что sum(1for m...должно быть sum(1 for m..., но я думаю , что есть и другие проблемы тоже. Не могли бы вы предоставить ссылку на онлайн-переводчика (например, tio ), чтобы продемонстрировать, как вы это называете, и показать, что это не ошибка?
Джеймс
@DJMcMayhem Я только что добавил ссылку, спасибо за предоставленную ссылку, я не был уверен, как это сделать. Я не получаю сообщение об ошибке при запуске там.
17
Ах, я не могу сказать, что вы вводили max(l)и min(l)как строки, поэтому я получаю ошибки. Спасибо за разъяснение этого! Хотя сейчас это на грани нарушения правила № 3, «обратите внимание, что эти различные значения должны использоваться (несколько) как логическое значение», но это определенно немного серой области.
Джеймс
Кстати, вот совет TIO: если вы поместите свои вызовы функций в поле нижнего колонтитула , они не будут учитываться при подсчете байтов, поэтому вы можете легко увидеть, как долго ваш ответ: попробуйте онлайн!
Джеймс
@DJMcMayhem Ах, спасибо. Я согласен, это что-то вроде серой зоны. Я мог бы взять 'max' и 'min' как true false, а затем сделать eval (c + '(l)'), который добавляет 6 байт и кажется более приемлемым, но пока OP не отвергает мой ответ, я предполагаю, что все в порядке.
Дилнан
2

JavaScript (ES6), 151 149 байт

g=
(s,f,a=[/\d/,/[A-Z]/,/[a-z]/,/[_\W]/],b=a.map(r=>s.split(r).length))=>s.replace(/./g,c=>b[a.findIndex(r=>r.test(c))]-Math[f?"max":"min"](...b)?' ':c)
<input id=s oninput=o.textContent=g(s.value,f.checked)><input id=f type=checkbox onclick=o.textContent=g(s.value,f.checked)><pre id=o>

К сожалению, правила, вероятно, не позволяют мне проходить Math.maxили Math.minкак флаг. Изменить: Сохранено 2 байта благодаря @JustinMariner.

Нил
источник
1

Желе , 37 байт

ØWṖs26µẎØṖḟW⁸;
¢f@³L$ÐṂFe@Ѐ³¬¹⁴?a³o⁶

Попробуйте онлайн!

-6 байт "позаимствовал" из поста Эрика: D

HyperNeutrino
источник
Lol сохранение пробелов - это, по сути, половина программы: D
Mr. Xcoder
Не могли бы вы добавить объяснение, или вы все еще работаете над его игрой в первую очередь?
Кевин Круйссен,
@KevinCruijssen Гольф первый: D
HyperNeutrino
1

Java (OpenJDK 8) , 307 + 34 306 + 27 295 байт

Мой «интересный» вызов.

Спасибо Кевину Круйссену за сокращение импортных байтов и полное исключение импорта!

s->b->{String t=s.replaceAll("\\d","2").replaceAll("[a-z]","0").replaceAll("[A-Z]","1").replaceAll("\\D","3"),v="";int a[]={0,0,0,0},i=0,z=0,y=-1>>>1;t.chars().forEach(j->{a[j%4]++;});for(int x:a){z=x>z?x:z;y=x<y?x:y;}for(;i<s.length();i++)v+=a[t.charAt(i)%4]!=(b?z:y)?" ":s.charAt(i);return v;}

Попробуйте онлайн!

Объяснение:

String t=s.replaceAll("\\d","2")
          .replaceAll("[a-z]","0")
          .replaceAll("[A-Z]","1")
          .replaceAll("\\D","3")

Сначала заменяет каждую группу целым числом от 0 до 3, используя некоторое простое регулярное выражение, и сохраняет его в новой строке.

int a[]={0,0,0,0},m,i=0,z=0,y=-1>>>1;

Инициализирует массив целых чисел, а также пару других целых чисел, которые будут использоваться позже. Устанавливает yпеременную в максимальный размер int, используя беззнаковое смещение вправо.

t.chars().forEach(j->{a[j%4]++;});

Для каждого символа в измененной строке используется значение ASCII по модулю 4 для вычисления индекса вышеупомянутого массива для приращения.

for(int x:a){
    z=x>z?x:z;
    y=x<y?x:y;
}

Затем он перебирает счетчики каждой группы, хранящейся в массиве, и вычисляет минимум ( y) и максимум ( z).

for(;i<s.length();i++)
    v+=a[t.charAt(i)%4]!=(b?z:y)?" ":s.charAt(i);

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

return v;

Наконец, верните новую строку!

Люк Стивенс
источник
1
Хороший ответ, +1 от меня! Две маленькие вещи для гольфа: import java.util.stream.IntStream;могут быть import java.util.stream.*;и ,iмогут быть, ,i=0после чего вы можете удалить i=0из цикла. Ох, и (s,b)->может быть s->b->.
Кевин Круйссен
@KevinCruijssen Спасибо! Я не понимал, что вы можете связать лямбды в цепи
Люк Стивенс
Это называется карри. :) Вы можете сделать это так java.util.function.Function<String, java.util.function.Function<Boolean, String>> g = s->b->{...};.
Кевин Круйссен,
1
Да, и еще одна вещь , чтобы играть в гольф: IntStream z=IntStream.of(a);m=(b?z.max():z.min()).getAsInt();может быть l=s.length(),x=0,y=lи for(int x:a){z=x>z?x:z;y=x<y?x:y;}и (b?z:y), поэтому вам больше не нужно импортировать. Собрать все вместе становится: s->b->{String t=s.replaceAll("\\d","2").replaceAll("[a-z]","0").replaceAll("[A-Z]","1").replaceAll("\\D","3"),v="";int a[]={0,0,0,0},i=0,l=s.length(),z=0,y=l;t.chars().forEach(j->{a[j%4]++;});for(int x:a){z=x>z?x:z;y=x<y?x:y;}for(;i<l;i++)v+=a[t.charAt(i)%4]!=(b?z:y)?" ":s.charAt(i);return v;}( 294 байта ) .
Кевин Круйссен,
1
@KevinCruijssen Оооооо приятно думать! Я мог бы немного подождать, прежде чем менять его на всякий случай, если вы придумаете что-нибудь еще;)
Люк Стивенс,
1

Баш, 229 227 212 байт

LANG=C;g="A-Z a-z 0-9 !A-Za-z0-9";declare -A H
f()(((i=$2?99:-1));r=$1;for h in $g;{ t=${r//[$h]};t=${#t};(($2?t<i:t>i))&&i=$t&&H=([$h]=1);((t-i))||H[$h]=1;};for h in $g;{((${H[$h]}))||r=${r//[$h]/ };};echo "$r")

Попробуйте онлайн

Науэль Фуйе
источник
Я не уверен, как пробелы вокруг скобок и квадратных блоков работают в Bash, но все равно, кажется, работает без пробела вf(){(( .
Кевин Круйссен
1
да, в общем случае пространство обязательно, за исключением того (, что можно сэкономить 2 байта, используя (вместо этого {
снижение
1

PHP, 161 158 байт

for([,$s,$z]=$argv;~$c=$s[$i++];)foreach([punct,upper,lower,digit]as$f)(ctype_.$f)($c)?$$i=$f:$g[$f]++;while(~$c=$s[$k++])echo$g[$$k]-($z?min:max)($g)?" ":$c;

Запустите -nrили попробуйте онлайн .

  • Первый контур: для каждой позиции, помните группу характера
    и подсчет вхождений групп , что текущий символ не в.
    (that negation saved 3 bytes)
  • depending on second parameter, pick min non-count for truthy, max non-count for falsy.
  • second loop: if (group of current character) non-count differs
    from min/max non-count then print space, else print character.
Titus
источник
1
@KevinCruijssen Make sure you have the latest PHP version (7.1.0) selected.
Titus
1

JavaScript (ES6), 139 bytes

s=>b=>s.map(c=>++a[g(c)]&&c,a=[0,0,0,0],g=c=>c>-1?0:/[a-z]/i.test(c)?c<"a"?2:1:3).map(c=>a.map(v=>v-Math[b?"max":"min"](...a))[g(c)]?" ":c)

Input and output is an array of characters. Takes actual boolean values for input.

A different approach from @Neil's answer; almost avoiding regular expressions. Instead, I used a series of checks to determine the category of each character:

  • Digits return true for c>-1 because non-digits fail mathematical comparisons
  • Uppercase letters match the regex /[a-z]/i and have codepoints less than "a"
  • Lowercase letters match that regex but have codepoints not less than "a"
  • Symbols pass none of those tests

Test Cases

Justin Mariner
источник