3ms Go with commentary


  • 0
    A
    func nearestPalindromic(s string) string {
    	l := len(s)
    	so, _ := strconv.ParseInt(s, 10, 64) // original
    	si := so / int64(math.Pow10(l/2))    // left half, as int
    
    	pal := func(i int64) int64 { // generate the palindrome, given left half
    		n := l*2 + 1 // n = number of 'positions', e.g. -1-2-3-4- -> 9 'positions'
    		b := make([]byte, l)
    		copy(b, []byte(strconv.FormatUint(uint64(i), 10)))
    		for lo, hi := n/2, n/2; lo > 0; lo, hi = lo-1, hi+1 { // Middle-out
    			b[hi/2] = b[lo/2] // hi is on the right-hand-side
    		}
    		u, _ := strconv.ParseInt(string(b), 10, 64)
    		return u
    	}
    
    	// Build the list of candidates; they must be in order from smallest to largest
    	candidates := []int64{}
    	candidates = append(candidates, int64(math.Pow10(l-1))-1) // 99..99
    	for _, i := range []int64{-1, 0, 1} {                     // "normal" cases: 1-smaller, same, 1-bigger
    		candidates = append(candidates, pal(si+i))
    	}
    	candidates = append(candidates, int64(math.Pow10(l))+1) // 10...01
    
    	// Find the best candidate, preferring the first (i.e. lowest) found in case of equal
    	min, best := math.MaxFloat64, int64(0)
    	for _, i := range candidates {
    		d := math.Abs(float64(so - i))
    		if i != so && min > d { // remove the case where we exactly match the original
    			min, best = d, i
    		}
    	}
    
    	return strconv.FormatInt(best, 10)
    }
    

Log in to reply
 

Looks like your connection to LeetCode Discuss was lost, please wait while we try to reconnect.