g | x | w | all
Bytes Lang Time Link
004Thunno 2 h230722T165214ZThe Thon
005Vyxal221128T005529Zemanresu
6564Regex Perl / PCRE190118T044621ZDeadcode
037Factor + math.primes.factors210328T033747Zchunes
5571Husk201115T132115ZDominic
009Stax201115T122656ZRazetime
009MathGolf190305T151756Zmaxb
005Brachylog190304T091840ZUnrelate
100ECMAScript 2016190123T162530ZM Dirr
044Charcoal190119T172830ZNeil
00605AB1E190118T112553ZKevin Cr
183Whispers v2181110T185153Zcaird co
007Pyth180908T100601ZMr. Xcod
058Julia180710T152426ZSundar R
008Japt g180709T100510ZShaggy
nanJelly170222T152326Zuser6213
020MATL noncompetitive151221T104640ZLuis Men
nanSeriously160201T044536Zuser4594
067Python 2150611T065324Zxnor
016J150324T052902Zalgorith
019J140820T120243ZFireFly
nanJava 8 422150308T025856ZMichael
039Mathematica140819T100821ZMartin E
161C#140821T155312ZRichard
084Python 2140823T014857Zxnor
262C# LINQ140820T091032Zldam
nan140821T101419Zisaacg
056Bash+coreutils140819T051219ZDigital
078 K140819T201355ZArthur B
129Regex140820T193119ZMartin E
166Lua140819T195239ZAdriweb
083Perl 5.10+140821T062706Zhobbs
062Ruby140820T170513Zhistocra
085PowerShell140820T183325ZRynant
083R140820T180636Zshadowta
113Ruby140820T002119ZJohn Ter
080Haskell140819T192609Zproud ha
170Clojure140819T011437ZMichael
120Haskell140819T130949ZTaylor F
095Python 2140819T004447Zisaacg
150Cobra140819T072253ZΟurous
095C140819T003957ZTodd Leh
176Lua140819T005212ZAndoDaan
013CJam140819T001652Zaditsu q

Thunno 2 h, 4 bytes

IÞfG

Try it online!

Explanation

IÞfG  # Implicit input
I     # Range between the inputs
 Þ    # Sorted by the following:
  f   #  Prime factors of the number
   G  #  Take the maximum of this list
      # Implicit output of first item

Vyxal, 5 bytes

ṡ‡ǐt∵

Try it Online!

ṡ     # Range from a to b
    ∵ # Minimum by...
 ‡--  # Next two as function
   t  # Last
  ǐ   # Prime factor

Regex (Perl / PCRE), 66 65 (64🐌) bytes

Inspired by seeing that both Martin Ender and jaytea, two regex geniuses, wrote regex solutions to this code golf, I wrote my own from scratch. The famous prime-checking regex does not appear anywhere in my solution.

Do not read this if you don't want some unary regex magic spoiled for you. If you do want to take a shot at figuring out this magic yourself, I highly recommend starting by solving some problems in ECMAScript regex:

  1. Match prime numbers (if you aren't already familiar with doing this in regex)
  2. Match powers of 2 (if you haven't already done so). Or just work your way through Regex Golf, which includes Prime and Powers. Make sure to do both the Classic and Teukon problem sets.
  3. Find the shortest way to match powers of N where N is some constant (i.e. specified in the regex, not the input) which can be composite (but is not required to be). For example, match powers of 6.

  4. Find a way of matching Nth powers, where N is some constant >=2. For example, match perfect squares. (For a warmup, match prime powers.)

  5. Match correct multiplication statements. Match triangular numbers.

  6. Match Fibonacci numbers (if you're as crazy as I am), or if you want to stick to something shorter, match correct statements of exponentiation (for a warmup, return as a match the logarithm in base 2 of a power of 2 – bonus, do the same for any number, rounding it however you like), or factorial numbers (for a warmup, match primorial numbers).

  7. Match abundant numbers (if you're as crazy as I am)

  8. Calculate an irrational number to requested precision (e.g. divide the input by the square root of 2, returning the rounded result as a match)

(The regex engine I wrote may be of help, as it is very fast at unary math regexes and includes a unary numerical mode which can test ranges of natural numbers (but also has a strings mode which can evaluate non-unary regexes, or unary with delimiters). By default it is ECMAScript compatible, but has optional extensions (which can selectively add subsets of PCRE, or even molecular lookahead, something that no other regex engine has).)

Otherwise, read on, and also read this GitHub Gist (warning, many spoilers) which chronicles the journey of pushing ECMAScript regex to tackle natural number functions of increasing difficulty (starting with teukon's set of puzzles, not all of them mathematical, which sparked this journey).

As with the other regex solutions to this problem, the input is given as two numbers in bijective unary, separated by a comma, representing an inclusive range. Only one number is returned. The regex could be modified to return all of the numbers that share the same smallest largest prime factor, as separate matches, but that would require variable-length lookbehind and either putting \K in a lookahead or returning the result as a capture instead of a match.

The technique used here of repeated implicit division by smallest prime factor is identical to that used in the Match strings whose length is a fourth power answer I posted a while back.

With no further ado:

((.+).*),(?!.*(?=\1)((?=(..+)(\4+$))\5)*(?!\2)).*(?=\1)\K(?3)*\2$

Try it online! - Perl
Try it online! - PCRE
Try it on regex101

And the free-spacing version, with comments:

                        # No ^ anchor needed, because this algorithm always returns a
                        # match for valid input (in which the first number is less than
                        # or equal to the second number), and even in /g mode only one
                        # match can be returned. You can add an anchor to make it reject
                        # invalid ranges.
                        
((.+).*),               # \1 = low end of range; \2 = conjectured number that is the
                        # smallest number in the set of the largest prime factor of each
                        # number in the range; note, it is only in subsequent tests that
                        # this is implicitly confined to being prime.
                        # We shall do the rest of our work inside the "high end of range"
                        # number.

(?!                     # Assert that there is no number in the range whose largest prime
                        # factor is smaller than \2.
  .*(?=\1)              # Cycle tail through all numbers in the range, starting with \1.

  # Subroutine call (?3) - defines one loop iteration, and needs to be called as (?3)*
  # Finds the largest prime factor of tail, and leaves it in tail. It will both be
  # evaluated here as-is, and later as a subroutine call. Here, it's followed by an
  # assertion that tail is less than something; if this fails to match, the regex
  # engine will try to backtrack, but that will never result in a match because
  # backtracking will only make tail larger.
  (                     # Repeatedly divide tail by its smallest prime factor, leaving
                        # only the largest prime factor at the end.

    (?=(..+)(\4+$))     # \5 = tool to make tail = \4 = largest nontrivial factor of
                        # current tail, which is implicitly the result of dividing it
                        # by its smallest prime factor.
    \5                  # tail = \4
  )*
  (?!\2)                # matches iff tail < \ 2
)

# At this point, \2 is guaranteed to be less than or equal to the smallest number in the
# set containing the largest prime factor of each of the numbers in the inputted range.
# The first time the regex engine reaches this point, \2 will be equal to the smallest
# number in that set, but if it backtracks, \2 will become smaller.

# now, pick a number in the range whose largest prime factor is \2
.*(?=\1)                # Cycle tail through all numbers in the range, starting with \1.
\K                      # Set us up to return tail as the match.
(?3)*                   # tail = largest prime factor of tail
\2$                     # Match iff tail == \2, then return the number whose largest
                        # prime factor is \2 as the match. If this fails to match, the
                        # regex engine will try to backtrack, but that will never result
                        # in a match, because backtracking makes tail a composite number
                        # that is larger than the largest prime factor of the currently
                        # marked return value, which makes it larger than any value \2
                        # can have.

Note that ((.+).*) can be changed to ((.+)+), dropping the size by 1 byte (from 65 to 64 bytes) with no loss of correct functionality – but the regex exponentially explodes in 🐌 slowness:

((.+)+),(?!.*(?=\1)((?=(..+)(\4+$))\5)*(?!\2)).*(?=\1)\K(?3)*\2$

Try it online! - Perl
Try it online! - PCRE

Regex (ECMAScript), 80 (79🐌) bytes

The algorithm can be easily ported to ECMAScript by replacing the subroutine call with a copy of the subroutine, and returning the match as capture group \6 instead of using \K. The result is 80 bytes in length:

((x+)x*),(?!.*(?=\1)((?=(xx+)(\4+$))\5)*(?!\2)).*(?=\1)(((?=(xx+)(\8+$))\9)*\2$)

Try it online! - 80 byte version
Try it online! - 79 byte exponential-slowdown 🐌 version (amazingly, this can handle all the test cases in 49 seconds)

Factor + math.primes.factors, 37 bytes

[ [a,b) [ factors last ] infimum-by ]

Try it online!

Explanation:

This is a quotation (anonymous function) that takes two integers from the data stack as input and leaves one integer on the data stack as output. Assuming 2001 2014 is on top of the data stack when this quotation is called...

Husk, 5 bytes = 5.71 characters

◄o▲p…

Try it online!

How?

◄       # element that minimizes result of
 o      # combining these 2 functions:
  ▲     # maximum of
   p    # prime factors
    …   # for the range from arg 1 ... arg 2

Stax, 9 bytes

üwπ┼♦Σjô≤

Run and debug it

Thought this would be shorter.

MathGolf, 9 bytes

↨áæ─g¶╙0§

Try it online!

Explanation

Could be 1-2 bytes shorter with a "get prime factorization" operator.

↨           pop a, b, loop from a to b (inclusive)
 á          sort by comparator
  æ         start block of length 4
   ─        get divisors
    g       pop a, (b), pop operator from code, filter
     ¶      is_prime(n)
      ╙     maximum of two elements, max of list, maximum by filter
       0    push 0
        §   get from array

Brachylog, 5 bytes

⟦₃ḋᵒh

Try it online!

Takes input as a list of two (or more, actually) values in no particular order, and outputs a single value through the output variable of the predicate (if you try to run it as a full program, it'll just print true. at you, unless you stick a w on the end). The input is interpreted as a Python-style range because to feed multiple values I need to give it a subscript no matter whether it's , , or so I may as well choose the one that matches the test cases.

    h The first item of
⟦₃    the range represented by the input
   ᵒ  after it's been sorted by
  ḋ   prime factorization.

Saves three bytes over the more obvious ⟦₃{ḋh}ᵒh by taking advantage of that Brachylog sorts its lists by elements first rather than lengths, such that the first step of sorting by prime factorizations is sorting by largest prime factors.

ECMAScript 2016 - 100 characters

m=>M=>(r=_=>M-m?[m,...r(++m)]:[])().sort((x,y)=>(s=(n,p=2)=>n>p?n%p?s(n,p+1):s(n/p,p):p)(x)-s(y))[0]

Definitely gets hurt by the lack of a built-in range.

This is a pretty standard anonymous function. It takes in a minimum (inclusive) and a maximum (exclusive), and then spits out the smallest smoothest number in that range.

Charcoal, 44 bytes

Nθ≔…θNη≔¹ζW¬№η¹«≦⊕ζW⊙η¬﹪λζUMη⎇﹪λζλ÷λζ»I⁺θ⌕η¹

Try it online! Link is to verbose version of code. Takes input as a half-open range and returns the lowest smoothest number from that range. Works by trial division of all the numbers in the range until at least one has become completely factorised (in which case it is the smoothest). Explanation:

Nθ

Input the lower end of the range.

≔…θNη

Create an array covering the whole range.

≔¹ζ

Set the initial factor to 1.

W¬№η¹«

Repeat until there is at least one 1 in the array.

≦⊕ζ

Increment the factor.

W⊙η¬﹪λζ

Repeat while at least one element is divisible by the factor.

UMη⎇﹪λζλ÷λζ»

Divide all divisible elements by the factor.

I⁺θ⌕η¹

Look up the (first) index of the 1, add on the lower end of the range, and print the result as a string.

05AB1E, 6 bytes

Input as a list of two items, outputs just one found integer in the [A,B] range (inclusive on both sides):

ŸΣfθ}н

Try it online or verify all test cases.

Explanation:

Ÿ          # Create a list in the inclusive range of the (implicit) input
           #  i.e. [9,15] → [9,10,11,12,13,14,15]
 Σ  }      # Sort it by:
  f        #  Get the prime factors
           #   i.e. 9 → [3]
           #   i.e. 10 → [2,5]
   θ       #  Pop and push the last item
           #   i.e. [3] → 3
           #   i.e. [2,5] → 5
           #  i.e. [9,10,11,12,13,14,15] → [9,12,10,15,14,11,13]
     н     # After sorting, pop and push the first item
           #  i.e. [9,12,10,15,14,11,13] → 9
           # (and output the result implicitly as result)

8 bytes alternative with same input-format, but outputs all found integers (as string) instead of one:

ŸDf€θWQÏ

Try it online or verify all test cases.

Explanation:

Ÿ          # Create a list in the inclusive range of the (implicit) input
           #  i.e. [9,15] → [9,10,11,12,13,14,15]
 D         # Duplicate this list
  f        # Get the prime factors of each
           #  i.e. [9,10,11,12,13,14,15] → [[3],[2,5],[11],[2,3],[13],[2,7],[3,5]]
   €θ      # Only leave the last value of each inner list
           #  i.e. [[3],[2,5],[11],[2,3],[13],[2,7],[3,5]] → [3,5,11,3,13,7,5]
     W     # Get the minimum of this list (without popping the list itself)
           #  i.e. [3,5,11,3,13,7,5] → 3
      Q    # Check for each value in the list if it is equal to this minimum
           #  i.e. [3,5,11,3,13,7,5] and 3 → [1,0,0,1,0,0,0]
       Ï   # Leave only the values of the duplicated list at the truthy indices
           #  i.e. [9,10,11,12,13,14,15] and [1,0,0,1,0,0,0] → ["9","12"]
           # (and output the result implicitly as result)

Whispers v2, 183 bytes

> Input
> Input
>> 1…2
>> ∤L
>> L’
>> Each 4 3
>> Select∧ 5 L
>> Each 7 6
>> Lⁿ10
> -1
>> Each 9 8
>> L‖R
>> Each 12 11 3
>> 13ᴺ
>> Each 9 14
> 0
>> 15ⁿ16
>> Output 17

Try it online!

Aside from revamping the algorithm, the only real golfing opportunity can be found on lines 9 and 10, but swapping them. When they're the other way round, the code is 1 byte longer, due to the repeated use of 9 or 10.

The structure tree for this program is:

tree

Red represents nilad lines, green represents function arguments. Arrows from \$a \to b\$ show the use of line \$a\$ as an argument for line \$b\$.

How it works.

We start at lines 1, 2 and 3. The first two simply take and store the inputs \$\alpha\$ and \$\beta\$ on lines 1 and 2 respectively. There two values are then passed to line 3, 1…2, which form the range

$$R := [\alpha, \alpha+1, ..., \beta-1, \beta]$$

As you can see from the tree above, \$R\$ is used in two places: line 6 and line 13. As line 6 eventually leads to line 13, we'll take the path down 6.

Line 6 is an Each statement, that maps a function (the first line reference) over an array (the second line reference). Here, the function is defined on line 4 as \$f(x) = \{i \: | \: (i | x), (i \le x), i \in \mathbb{N}\}\$ i.e. the array of \$x\$'s divisors. The array is \$R\$, so line 6 iterates over \$R\$, returning the divisors of each integer, forming a new array

$$D := [f(\alpha), f(\alpha+1), ..., f(\beta-1), f(\beta)]$$

We then get more complicated as we skip down to line 8. Line 8 is also an Each statement, but its function argument, line 7 is split over two lines, 7 and 5:

>> L’
>> Select∧ 5 L

Mathematically, this is the function \$g(A) = \{i \: | \: (i \in \mathbb{P}), (i \in A)\}\$, that takes a set \$A\$ and returns all the primes in \$A\$. Line 8 is iterating over \$D\$, essentially filtering all composite numbers from each subarray in \$D\$, to form

$$A := [g(f(\alpha)), g(f(\alpha+1)), ..., g(f(\beta-1)), g(f(\beta))]$$

Then, we encounter yet another Each statement on line 11, which iterates line 9 over \$A\$. Line 9 takes an array and returns the final element of that array. As \$g(A)\$ returns the array sorted, this is equivalent to return the largest value in that array. At this point, we remember that \$g(f(x))\$ returns the list of prime factors of \$x\$, so line 9 maps each \$x\$ to its largest prime factor, returning

$$B := [\max(g(f(\alpha))), \max(g(f(\alpha+1))), ..., \max(g(f(\beta-1))), \max(g(f(\beta)))]$$

Once we have \$B\$, we now have an array we can sort \$R\$ by, e.g. we sort each value \$x\$ in \$R\$ by the resulting value of \$\max(g(f(x)))\$. However, we do not have a sort-by command in Whispers, only the simple Python sort(list). Luckily, due to how sort sorts lists of lists, we can concatenate each \$x\$ with \$\max(g(f(x))\$ and sort by the first element, what Python does naturally.

Lines 12 and 13 perform this concatenation, by iterating a concatenate function (line 12) over \$B\$ and \$R\$. This forms an array of pairs of numbers, in the form \$[\max(g(f(x))), x]\$. Next, we sort this array on line 14, which, due to the way Python compares lists, places the numbers with the lowest largest prime factor towards the end.

Almost finished. The only things left to do are to extract \$R\$, sorted by \$B\$ (we'll call this array \$R_B\$. This is done simply by taking the last element of each subarray (line 9 already does this for us, so we simply need Each 9 14 on line 15, rather than defining a new function). Once that's done, we simply take the first element in \$R_B\$, which will be (one of) the number with the lowest largest prime factor i.e. the smoothest number.

Pyth, 7 bytes

.mePbrF

Try it here!

Outputs all smooth integers in the range \$[a, b)\$. For the smooth integers in \$[a, b]\$, just use } in place of r.

.mePbrF – Full program with arguments a and b.
     rF – Fold by half-inclusive range. Yields the integers in [a, b).
.m      – Values b in that list which give minimal results when applied f.
  ePb   – function / block f. 
   Pb   – Prime factors of b.
  e     – Last element. This is guaranteed to yield the largest, as they're sorted.

Julia, 58 bytes

using Primes
!r=[r;][indmin(max(factor(Set,n)...)for n=r)]

Takes a Range object of the form 5:9 as input, returns the smallest of the smoothest numbers in the range. (No TIO link, because TIO doesn't seem to have the Primes package.)

Japt -g, 8 bytes

õV ñ_k Ì

Try it


Explanation

             :Implicit input of integers U & V
õV           :Range [U,V]
   ñ_        :Sort by passing each through a function
     k       :  Prime factors
       Ì     :  Last element
             :Implicitly output the first element in that array

Jelly, 7 bytes, score = 7÷7×8 = 8, language postdates challenge

rÆfṀ$ÐṂ

Try it online!

Takes the lower and upper range endpoints as two separate arguments. Outputs a list of all the smoothest numbers in the range. (This can be viewed as a function, in which case the output is a Jelly list, or as a full program, in which case the output happens to use the same list representation that JSON does.)

Explanation

Those times when your Jelly program is just a literal translation of the spec…

rÆfṀ$ÐṂ
r        Range from {first argument} to {second argument}
     ÐṂ  Return the elements which have the minimum
   Ṁ$      largest
 Æf          prime factor

MATL (non-competitive), 20 bytes

This language was designed after the challenge

Range is inclusive at both ends. The numbers are taken as two separate inputs.

2$:t[]w"@YfX>v]4#X<)

Try it online!

Explanation

2$:          % implicitly input two numbers. Inclusive range
t            % duplicate                      
[]           % empty array
w            % swap elements in stack         
"            % for each                  
  @          %   push loop variable
  Yf         %   prime factors                  
  X>         %   maximum value
  v          %   vertical concatenation         
]            % end for each                         
4#X<         % arg min 
)            % index with this arg min into initial range of numbers

Seriously, 8*14/7 = 16 (non-competitive)

,x;`yM`M;m@í@E

Seriously was created after this challenge, but I wanted to post this answer because it exemplifies the type of challenges Seriously is good at.

Try it online!

Explanation:

,x;`yM`M;m@í@E
,x;             make two copies of range(a,b) (a,b = input())
   `  `M;       make two copies of the result of the map:
    yM            push maximum prime factor
         m@í    push index of minimum element from prime factors
            @E  push element from range with given index

Python 2, 67

f=lambda R,F=1,i=2:[n for n in range(*R)if F**n%n<1]or f(R,F*i,i+1)

Thinking about another golf gave me an idea for a new algorithm to check smoothness, hence the late answer.

The prime factorization of the factorial i! includes exactly the primes at most i. So, if n is a product of distinct primes, its smoothness (largest prime factor) is the smallest i for which n is a divisor of i!. To account for repeated prime factors in n, we can instead use a sufficiently high power of i!. In particular, (i!)**n suffices.

The code tries increasing factorials F=i!, updated recursively. We filter for the divisors of F in the input range, and output them if there are any, and otherwise move on to (i+1)!.

Test case:

>> f([157, 249])
[162, 192, 216, 243]

J - 16 char

Using the (start, length) style of range, as allowed by the comments.

(0{+/:{:@q:@+)i.

To be used as a dyadic verb: left argument is start, right is length.

   5 (+)i. 6              NB. range
5 6 7 8 9 10
   5 (q:@+)i. 6           NB. prime factorizations
5 0 0
2 3 0
7 0 0
2 2 2
3 3 0
2 5 0
   5 ({:@q:@+)i. 6        NB. largest prime factors
5 3 7 2 3 5
   5 (+/:{:@q:@+)i. 6     NB. sort range by smallest factors
8 6 9 5 10 7
   5 (0{+/:{:@q:@+)i. 6   NB. take first entry
8
   f=:(0{+/:{:@q:@+)i.    NB. can also be named
   2001 f 13
2002

A (start, end) solution is +2 chars, and excludes the end; including the end is +2 more. But on the bright side, it looks rather nice since we match up all the {braces}.

(0{}./:{:@q:@}.)i.    NB. excluding
(0{}./:{:@q:@}.)1+i.  NB. including

J, 22 20 19 chars

({.@/:{:@q:)@(}.i.)

E.g.

   2001 ({.@/: {:@q:)@(}. i.) 2014
2002

(Functions taking two arguments are infix in J.)

Java 8 - 422 454 chars

I'm learning Java 8, and wanted to give this a shot relative to Java (or even Java 8 streams).

Compared to other languages, this is brutal but an interesting exercise.

Golfed:

import java.util.stream.*;import java.math.*;
class F{int v;int i;public int getV() { return v; }
F(int i){this.i = i;v=IntStream.range(2,i+1).map(j->((i%j==0)&&new BigInteger(""+j).isProbablePrime(1))?j:0).max().getAsInt();}}
public class T{
int s(int a, int b){return IntStream.range(a,b+1).boxed().map(F::new).sorted(java.util.Comparator.comparingInt(F::getV)).collect(java.util.stream.Collectors.toList()).get(0).i;}}

Ungolfed:

import java.util.stream.*;
import java.math.*;

class F {
    int v;
    int i;
    public int getV() { return v; }
    F (int i) { 
        this.i = i;
        v = IntStream.range(2,i+1)
                     .map( j -> ((i%j==0) && 
                           new BigInteger(""+j).isProbablePrime(1))?j:0)
                     .max()
                     .getAsInt();
    }
}

public class T {
    int s(int a, int b) {
        return IntStream.range(a,b+1)
                    .boxed()
                    .map(F::new)
                    .sorted(java.util.Comparator.comparingInt(F::getV))
                    .collect(java.util.stream.Collectors.toList())
                    .get(0).i;
    }
}

example run using:

public static void main(String[] s) {
    System.out.println(new T().s(157,249));
}

192

Mathematica, 61 45 39 characters

Range@##~MinimalBy~Last@*FactorInteger&

Very straightforward implementation of the spec as an unnamed function.

C#, 240 234 226 161 characters


int S(int i,int b){int s=2<<29,n=0,k,j,p;for(k=i;i<b;k=++i){for(;k>1;--k){if(i%k<1){p=1;for(j=2;j<k;++j)if(k%j<1)p=0;if(p>0)break;}}if(k<s){s=k;n=i;}}return n;}}


Acknowledgements & Reduction Explanations
- Thanks to CodesInChaos for reductions to 226, see comments for specifics
- Reduced to 161 after re-reading the rules and seeing that a mere function is allowed (i.e., a free-standing program is not required.)

Usage
function:
- input: two integers
- output: if multiple valid answers exist, returns the smallest


Explanation (with comments and runnable test-wrapper)

class Test
{
    int S(int i, int b)
    {
        //s = lowest gpf found so far
        //n = best answer so far
        //i = range iterator
        //p = prime indicator (1=true, 0=false)
        int s = 2 << 29, n = 0, k, j, p;
        for(k=i; i<b; k=++i)
        {
            //iterate through the factors of i
            for(;k>1;--k)
            {
                if (i % k < 1)
                {
                    p=1;
                    //determine if k is prime
                    for (j = 2; j < k; ++j)
                        if (k % j < 1)
                            p = 0;
                    if (p>0) break;
                }
            }
            if (k < s)
            {
                s = k;
                n = i;
            }
        }
        return n;
    }

    public static void Main(string[] args)
    {
        var d = new D();
        System.Diagnostics.Debug.Assert(d.S(5, 11) == 8);
        System.Diagnostics.Debug.Assert(d.S(9, 16) == 9);
        System.Diagnostics.Debug.Assert(d.S(9, 17) == 16);
        System.Diagnostics.Debug.Assert(d.S(157, 249) == 162);
        System.Diagnostics.Debug.Assert(d.S(2001, 2014) == 2002);
    }
}

Python 2 (84)

f=lambda n,p=2:n>1and f(n/p**(n%p<1),p+(n%p>0))or p
print min(range(*input()),key=f)

@isaacg's solution, but with a min by function key in place of explicit min-finding, and a recursive function playing the role of the iteration.

Run in Stackless Python to avoid recursion limits.

It looks wasteful to use the paranthesized condition (n%p<1), then repeat its negation also in parantheses (n%p>0), but that was the best I got. I tried things a bunch of things, but they turned out worse.

f(n/p**(n%p<1),p+(n%p>0))     # Current for comparison
f(*[n/p,n,p,p+1][n%p>0::2])
n%p and f(n,p+1)or f(n/p,p)
f(*n%p and[n,p+1]or[n/p,p])

I welcome any improvements you can think of.

C# LINQ: 317 303 289 262

using System.Linq;class P{static void Main(string[]a){System.Console.Write(Enumerable.Range(int.Parse(a[0]),int.Parse(a[1])).Select(i=>new{i,F=F(i)}).Aggregate((i,j)=>i.F<j.F?i:j).i);}static int F(int a){int b=1;for(;a>1;)if(a%++b<1)while(a%b<1)a/=b;return b;}}

Ungolfed:

using System.Linq;

class P
{
  static void Main(string[]a)
  {
    System.Console.Write(
      Enumerable.Range(int.Parse(a[0]), int.Parse(a[1])) //create an enumerable of numbers containing our range (start, length)
        .Select(i => new { i, F = F(i) }) //make a sort of key value pair, with the key (i) being the number in question and the value (F) being the lowest prime factor
        .Aggregate((i, j) => i.F < j.F ? i : j).i); //somehow sort the array, I'm still not entirely sure how this works
  }
  static int F(int a)
  {
    int b=1;
    for(;a>1;)
      if(a%++b<1)
        while(a%b<1)
          a/=b;
    return b;
  }
}

It takes in the start and the length from the command line and will return the largest smooth number.

I used answers from here and here to make my answer.

Thanks to VisualMelon for tweaking it and shaving 12 bytes off! I also got rid of the braces in the if saving 2 bytes, and CodeInChaos pointed out some obvious stuff I missed (thanks again).

Note: This answer is not allowable.

This answer uses multiple features of Pyth added after the challenge was asked.

I added another new feature, calling unary range on a 2 element tuple, which shortens the solution by two characters, to this:

Pyth, 7

hoePNUQ

Input is now taken comma separated. The rest is the same.


This answer uses a feature of Pyth that was added after this question was asked, specifically after seeing @aditsu's wonderful CJam solution. That being said, I wanted to demonstrate what adding that feature has made possible. The feature is P, which is an arity-1 function which on integer input returns a list of all prime factors of the input, sorted smallest to largest.

Pyth, 9

hoePNrQvw

Uses Python-style ranges, newline separated on STDIN. Outputs smallest solution to STDOUT.

Explanation:

      Q = eval(input())                         Implicit, because Q is present.
h     head(                                     First element of
 o         order_by(                            Sort, using lambda expression as key.
                    lambda N:                   Implicit in o
  e                          end(               Last element of
   PN                            pfact(N)),     List containing all prime factors of N.
  r                 range(                      Python-style range, lower inc, upper exc.
   Q                      Q,                    A variable, initialized as shown above.
   vw                     eval(input()))))      The second entry of the range, same way.

Tests:

$ newline='
'

$ echo "9${newline}16" | ./pyth.py -c 'hoePNrQvw'
9

$ echo "9${newline}17" | ./pyth.py -c 'hoePNrQvw'
16

$ echo "157${newline}249" | ./pyth.py -c 'hoePNrQvw'
162

$ echo "2001${newline}2014" | ./pyth.py -c 'hoePNrQvw'
2002

Bash+coreutils, 56 bytes

seq $@|factor|sed 's/:.* / /'|sort -nk2|sed '1s/ .*//;q'

Input is from from exactly two command-line arguments (Thanks @nyuszika7h !!!). Output is a singular result printed to STDOUT.

Output:

$ ./smooth.sh 9 15
12
$ ./smooth.sh 9 16
16
$ ./smooth.sh 157 249
162
$ ./smooth.sh 2001 2014
2002
$ 

Note ranges in this context are inclusive of both endpoints.

Q, 91 characters K, 78 characters

{(x+{where x=min x}{(-2#{x div 2+(where 0=x mod 2_til x)@0}\[{x>0};x])@0}'[(x)_til y+1])@0}

k would probably shave a dozen characters

edit: indeed, treating the upper bound as non inclusive this time

{*:x+{&:x=min x}{*:-2#{6h$x%2+*:&:x={y*6h$x%y}[x]'[2_!x]}\[{x>0};x]}'[(x)_!y]}

Regex (.NET PCRE flavour), 183 129 bytes

Don't try this at home!

This is not really a contender for the win. But Eric Tressler suggested solving this problem with nothing but a regex, and I couldn't resist giving it a go. This might be is possible in PCRE as well (and even shorter, see below), but I chose .NET because my solution needs arbitrary-length lookbehinds. Here we go:

(?<=^(1+),.*)(?=\1)(?=((11+)(?=.*(?=\3$)(?!(11+?)\4+$))(?=\3+$)|(?!(11+)\5+$)1+))(?!.+(?=\1)(?:(?!\2)|(?=((11+)(?=.*(?=\7$)(?!(11+?)\8+$))(?=\7+$)|(?!(11+)\9+$)1+)).*(?=\2$)(?=\6)))1+

The input is encoded as an inclusive comma-separated range, where both numbers are given in unary notation using 1s. The match will be the trailing S 1s where S is the smoothest number in the range. Ties are broken in favour of the smallest number.

So the second example from the question would be the following string (match underlined)

111111111,1111111111111111
                 =========

It is based on the (by now rather well-known) prime-checking regex, variations of which are embedded in there a whopping 6 times.

Here is a version using free-spacing and comments for those who want to know what's going on.

# Note that the beginning of the match we're looking for is somewhere
# in the second part of the input.
(?<=^(1+),.*)          # Pick up the minimum range MIN in group 1
(?=\1)                 # Make sure there are at least MIN 1s ahead

                       # Now there will be N 1s ahead of the cursor
                       # where MIN <= N <= MAX.


(?=(                   # Find the largest prime factor of this number
                       # store it in group 2.
  (11+)                # Capture a potential prime factor P in group 3
  (?=                  # Check that it's prime
    .*(?=\3$)          # Move to a position where there are exactly 
                       # P 1s ahead
    (?!(11+?)\4+$)     # Check that the remaining 1s are not composite
  )
  (?=\3+$)             # Now check that P is a divisor of N.
|                      # This does not work for prime N, so we need a 
                       # separate check
  (?!(11+)\5+$)        # Make sure that N is prime.
  1+                   # Match N
))

(?!                    # Now we need to make sure that here is not 
                       # another (smaller) number M with a smaller 
                       # largest prime factor

  .+                   # Backtrack through all remaining positions
  (?=\1)               # Make sure there are still MIN 1s ahead

  (?:
    (?!\2)             # If M is itself less than P we fail 
                       # unconditionally.
  |                    # Else we compare the largest prime factors.
    (?=(               # This is the same as above, but it puts the
                       # prime factor Q in group 6.
      (11+)
      (?=
        .*(?=\7$)
        (?!(11+?)\8+$)
      )
      (?=\7+$)
    |
      (?!(11+)\9+$)
      1+
    ))
    .*(?=\2$)          # Move to a position where there are exactly 
                       # P 1s ahead
    (?=\6)             # Try to still match Q (which means that Q is
                       # less than P)
  )
)
1+                     # Grab all digits for the match

You can test it online over here. Don't try too large inputs though, I make no guarantees about the performance of this monster.

Edit:

I ended up porting this to PCRE (which only requires two steps), and shortening the regex by almost a third. Here is the new version:

^(1+),.*?\K(?=\1)(?=((11+)(?=.*(?=\3$)(?!(11+?)\4+$))(?=\3+$)|(?!(11+)\5+$)1+))(?!.+(?=\1)(?:(?!\2)|(?=((?2))).*(?=\2$)(?=\6)))1+

This is essentially the same, with two changes:

Lua - 166 chars

I don'tdidn't have (yet!) enough reputation to comment on AndoDaan's solution, but here are some improvements on his code

a,b=io.read("*n","*n")s=b for i=a,b do f={}n=i d=2 while n>1 do while n%d<1 do f[#f+1]=d n=n/d end d=d+1 end p=math.max(unpack(f))if p<s then s=p c=i end end print(c)

Changes :

Perl (5.10+), 83

for(<>..<>){$n=$_;$p=2;$_%$p&&$p++or$_/=$p while$_>1;$m=$p,$r=$n if$p<$m||!$m}
say$r

(linebreak can be removed). Takes two endpoints of an inclusive range on two lines of stdin (because <> is cheaper than accessing ARGV) and outputs the smoothest to stdout. If there's a tie for smoothest, prints the smallest. Could print the biggest at the cost of one character.

The algorithm is basically isaacg's way of finding the greatest prime factor, although we came up with it independently. That part golfs down beautifully to a single statement in perl, the rest has more overhead than I'd like though.

Should be run under perl -E or with a use 5.012 preamble. If you can't do that, replace say$r with print$r,$/.

Ruby, 65 62

require'prime'
s=->a,b{(a..b).min_by{|x|x.prime_division[-1]}}

With apologies to https://codegolf.stackexchange.com/a/36484/6828, this is the golfed (and slightly simplified) version of that. Uses an inclusive range since it's a character shorter.

1.9.3-p327 :004 > s[157,249]
 => 192 
1.9.3-p327 :005 > s[5,11]
 => 8 
1.9.3-p327 :006 > s[9,15]
 => 12 
1.9.3-p327 :007 > s[9,16]
 => 16 

And thanks to YenTheFirst for saving three characters.

PowerShell - 85

($args[0]..$args[1]|sort{$d=2
while($_-gt1){while(!($_%$d)){$m=$d;$_/=$d}$d++}$m})[0]

This will sort a range of numbers (inclusive) based on each number's max prime factor. It returns the lowest sorted element.

> smooth 5 10
8
> smooth 9 15
12
> smooth 9 16
16
> smooth 157 248
243
> smooth 2001 2013
2002

R, 83

library(gmp)
n=a:b
n[which.min(lapply(lapply(lapply(n,factorize),max),as.numeric))]

where the bottom of the input range is assigned to a and the top (inclusive) is assigned to b.

gmp is a package that is available on CRAN. It felt dirty until I saw that absurd mf function in CJam. Install by typing install.packages("gmp") in the console.

Ruby - 113 chars

Using the stdlib. Returns one result. Tested on ruby 2.1.2.

require 'prime'
def smooth_range(a,b)
  (a...b).sort_by{|e|e.prime_division.flat_map{|f,p|[f]*p}.uniq.max}[0]
end

Haskell, 96 94 93 86 80 characters

x%y|x<2=y|mod x y<1=div x y%y|0<1=x%(y+1)
a#b=snd$minimum$map(\x->(x%2,x))[a..b]

usage via GHCi (a Haskell shell):

>5 # 9
8
>9 # 15
9

EDIT: now a much simpler algorithm.

this solution includes both numbers in the range (so 8 # 9 and 7 # 8 are both 8)

explanation:

the (%) function takes two parameters, x and y. when y is 2, the function returns the smoothness of x.

the algorithm from here is simple - get the combined list of all smoothnesses of numbers in the input with each smoothness storing a reference to it's original number, sort then to get the smallest, and return it's referenced number.


here is an ungolfed javascript version with the same algorithm:

function smoothness(n,p)
{
    p = p || 2
    if (x == 1)
        return p
    if (x % p == 0)
        return smoothness(x/p, p)
    else
        return smoothness(x,p+1);
}
function smoothnessRange(a, b)
{
    var minSmoothness = smoothness(a);
    var min=a;
    for(var i=a+1;i <= b;i++)
        if(minSmoothness > smoothness(i))
        {
            minSmoothness = smoothness(i)
            min = i
        }
    return min;
}

Clojure - 173 170 chars

I'm a Clojure newbie. Golfed:

(defn g[x,d](if(and(= 0(mod x d))(.isProbablePrime(biginteger d) 1))d 0))(defn f[i](apply max-key(partial g i)(range 2(inc i))))(defn s[a,b](first(sort-by f(range a b))))

Sample runs:

Ranges include low-end, exclude high-end: [a,b) Only prints one of the smoothest numbers, if multiple occur.

(println (s 5 11))
(println (s 9 16))
(println (s 9 17))
(println (s 157, 249))
(println (s 2001, 2014))

yields:

bash$ java -jar clojure-1.6.0.jar range.clj
8
9
16
192
2002

Ungolfed:

(defn g [x,d] (if (and (= 0(mod x d)) (.isProbablePrime (biginteger d) 1)) d 0))
(defn f [i] (apply max-key (partial g i) (range 2 (inc i))))
(defn s [a,b] (first (sort-by f (range a b))))

Haskell - 120

import Data.List
import Data.Ord
x!y=(minimumBy(comparing(%2)))[x..y]
x%y|x<y=y|x`mod`y==0=(x`div`y)%y|otherwise=x%(y+1)

Example usage:

> 5 ! 10
8
> 9 ! 15
9
> 9 ! 16
16
> 157 ! 248
162
> 2001 ! 2013
2002

Python 2, 95

i=input()
for a in range(*i):
 s=a;p=2
 while~-a:b=a%p<1;p+=1-b;a/=p**b
 if p<i:i=p;j=s                                        
print j

Finds the smoothness of the the numbers by trial division until the number is 1. i stores the smallest smoothness so far, j stores the number that gave that smoothness.

Thanks to @xnor for the golfs.

Cobra - 150

def f(r as vari int)
    x,y=r
    c,o=y,0
    for n in x:y,for m in n:0:-1
        p=1
        for l in 2:m,if m%l<1,p=0
        if n%m<=0<p
            if m<c,c,o=m,n
            break
    print o

Not even sure why I bothered, cobra just can't compete here.

C,  149   95

Edited answer:

I cannot claim credit for this solution. This updated answer borrows the beautiful method used by isaacg in his Python solution. I wanted to see if it was possible to write it in C as a nested for/while loop with no curly braces, and it is!

R(a,b,n,q,p,m){for(;a<b;m=p<q?a:m,q=p<q?p:q,n=++a,p=2)while(n>1)if(n%p)p++;else n/=p;return m;}

Explanation:


Original answer:

This was my original answer...

P(n,f,p){for(;++f<n;)p=p&&n%f;return p;}
G(n,f){for(;--f>1;)if(n%f==0&&P(f,1,1))return f;}
R(a,b,p,n){for(;++p;)for(n=a;n<b;n++)if(G(n,n)==p)return n;}

Explanation:

Test driver:

test(a,b){printf("smooth_range(%d, %d)\n%d\n",a,b,S(a,b,1,0));}
main(){test(5,11);test(9,16);test(9,17);test(157,249);test(2001,2014);}

Output:

smooth_range(5, 11)
8
smooth_range(9, 16)
9
smooth_range(9, 17)
16
smooth_range(157, 249)
162
smooth_range(2001, 2014)
2002

Lua - 176 characters

a,b=io.read("*n","*n")s=b for i=a,b do f={}n=i d=2 while n>1 do while n%d==0 do table.insert(f, d)n=n/d end d=d+1 end p=math.max(unpack(f))if p<s then s=p c=i end end print(c)

I really should stop golfing in Lua. There's no point.

CJam - 13

q~,>{mfW=}$0=

Try it at http://cjam.aditsu.net/

Example input: 2001 2014
Example output: 2002

Explanation:

q~ reads and evaluates the input, pushing the 2 numbers on the stack (say min and max)
, makes an array [0 1 ... max-1]
> slices the array starting at min, resulting in [min ... max-1]
{…}$ sorts the array using the block to calculate the sorting key
mf gets an array with all the prime factors of a number, in order
W= gets the last element of the array (W=-1), thus obtaining the largest prime factor to be used as a sorting key
0= gets the first element of the (sorted) array