Какой самый эффективный способ определить длину самого длинного элемента в списке? - PullRequest
3 голосов
/ 02 марта 2009

Учитывая список слов различной длины, каков наилучший способ найти максимальную длину слов?

Например, следующее должно возвращать 6

findMaxLen("a,set,of,random,words")


Конечно, это довольно тривиально ...

<cffunction name="findMaxLen" returntype="Numeric">
    <cfset var CurMax = 0 />
    <cfset var CurItem = 0 />
    <cfloop index="CurItem" list="#Arguments[1]#">
        <cfif Len(CurItem) GT CurMax >
            <cfset CurMax = Len(CurItem)/>
        </cfif>
    </cfloop>
    <cfreturn CurMax />
</cffunction>

1011 *
*

Или немного короче ...

<cffunction name="findMaxLen" returntype="Numeric">
    <cfset var CurMax = 0 />
    <cfset var CurItem = 0 />
    <cfloop index="CurItem" list="#Arguments[1]#">
        <cfset CurMax = Max( CurMax , Len(CurItem) ) />
    </cfloop>
    <cfreturn CurMax />
</cffunction>


Но есть ли лучший способ - что-то более эффективное?

Возможно, какой-нибудь Java-метод? Преобразование в массив и сортировка по длине элемента? Считаете самый большой разрыв между запятыми?


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

Ответы [ 14 ]

11 голосов
/ 02 марта 2009

Посчитайте расстояние между запятыми.

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

int FindLongestWord(char* str)
{
   char* lastComma = str - 1;
   int longest = 0;
   int length;
   char* pCheckChar;

   for(pCheckChar = str; *pCheckChar; pCheckChar++)
   {
      if(*pCheckChar == ',')
      {
         length = pCheckChar - lastComma - 1;
         if(length > longest)
         {
            longest = length;
         }

         lastComma = pCheckChar;
      }
   }

   // Check to see if the last word is the longest
   length = pCheckChar - lastComma - 1;
   if(length > longest)
   {
      longest = length;
   }

   return longest;
}

или я полагаю, вы могли бы просто сказать

"a,set,of,random,words".Split(',').Max(w=>w.Length);

если мы играем в игры ...;]

2 голосов
/ 03 марта 2009

В Perl (при условии, что у нас есть переменная $max, в которой должен храниться ответ):

(length $1 > $max) && ($max = length $1) while "a,set,of,random,words" =~ /(\w+)/g;

Или:

(length $_ > $max) && ($max = length $_) foreach split /,/, "a,set,of,random,words";

Или:

$max = length((sort { length $b <=> length $a } split /,/, "a,set,of,random,words")[0]);

TMTOWTDI, в конце концов.

РЕДАКТИРОВАТЬ: я забыл о модулях ядра!

use List::Util 'reduce';
$max = length reduce { length $a > length $b ? $a : $b } split /,/, "a,set,of,random,words";

... который каким-то образом умудряется быть длиннее других. О, хорошо!

РЕДАКТИРОВАТЬ 2: Я только что вспомнил map():

use List::Util 'max';
$max = max map length, split /,/, "a,set,of,random,words";

Это больше похоже на то, что я ищу.

РЕДАКТИРОВАТЬ 3: И только для полноты:

($max) = sort { $b <=> $a } map length, split /,/, "a,set,of,random,words";
1 голос
/ 03 марта 2009

А вот и «короткий» путь CFML - 72 символа ...

Len(ArrayMax("a,set,of,random,words".replaceAll('[^,]','1').split(',')))

Другая версия, 78 символов, но обрабатывает огромные строки (см. Комментарии) ...

Len(ListLast(ListSort("a,set,of,random,words".replaceAll('[^,]','1'),'text')))
1 голос
/ 02 марта 2009

Учитывая, что есть тег code-golf, вот 52 символа в C #

"a,set,of,random,words".Split(',').Max(w=>w.Length);
0 голосов
/ 08 июля 2016

Разве это не будет самым простым?

<cffunction name="findMaxLen" returntype="Numeric">
    <cfset longest = 0>
    <cfloop list="#Arguments[1]#" index="w">
        <cfif len(w) gt longest>
            <cfset longest = len(w)>
        </cfif>
    </cfloop>
    <cfreturn longest>
</cffunction>
0 голосов
/ 05 июля 2016

У меня нет Python передо мной, поэтому я не могу проверить это работает, но ...

def maxlen(x):
    return len(sorted(x.split(), key=lambda y: len(y))[1])

Должен сделать свое дело.

0 голосов
/ 25 сентября 2009

Clojure: 49 байтов.

(def l #(reduce max(for[x(.split%%2)](count x))))

Разборчивая версия:

(defn longest [astr sep]
  (reduce max
    (for [word (.split astr sep)]
      (count word))))

Я все еще изучаю язык, поэтому я хотел бы услышать любые способы улучшить его.

0 голосов
/ 11 июня 2009

В скале (55 символов):

",set,of,random,words".split(",").:\(0)(_.length max _)
0 голосов
/ 11 мая 2009

В J

Допустим, список строк в штучной упаковке (L):

{.\:~>#&.>L

Пример использования файла CSV:

{.\:~;>#&.>readcsv'test.csv'
0 голосов
/ 11 мая 2009

в vc ++

int findMaxLen(const char *s)
{
    const char c = ',';
    int a = 0, b = 0;
    while(*s)
    {
        while(*s && *s++ != c)b++;
        if(b > a)a=b;
        b = 0;
    }
    return a;
}
...