Compare commits
No commits in common. "e1b702657ca68b9a5af4b256401f1e85f65878b0" and "ed8cd12d2599be85534e44b1b023778523fb4309" have entirely different histories.
e1b702657c
...
ed8cd12d25
44 changed files with 0 additions and 936 deletions
24
LICENSE
24
LICENSE
|
|
@ -1,24 +0,0 @@
|
||||||
This is free and unencumbered software released into the public domain.
|
|
||||||
|
|
||||||
Anyone is free to copy, modify, publish, use, compile, sell, or
|
|
||||||
distribute this software, either in source code form or as a compiled
|
|
||||||
binary, for any purpose, commercial or non-commercial, and by any
|
|
||||||
means.
|
|
||||||
|
|
||||||
In jurisdictions that recognize copyright laws, the author or authors
|
|
||||||
of this software dedicate any and all copyright interest in the
|
|
||||||
software to the public domain. We make this dedication for the benefit
|
|
||||||
of the public at large and to the detriment of our heirs and
|
|
||||||
successors. We intend this dedication to be an overt act of
|
|
||||||
relinquishment in perpetuity of all present and future rights to this
|
|
||||||
software under copyright law.
|
|
||||||
|
|
||||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
||||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
||||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
|
||||||
IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
|
||||||
OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
|
||||||
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
|
||||||
OTHER DEALINGS IN THE SOFTWARE.
|
|
||||||
|
|
||||||
For more information, please refer to <https://unlicense.org/>
|
|
||||||
4
Makefile
4
Makefile
|
|
@ -1,4 +0,0 @@
|
||||||
lint:
|
|
||||||
golangci-lint run ./...
|
|
||||||
|
|
||||||
.PHONY: lint
|
|
||||||
21
create.sh
21
create.sh
|
|
@ -1,21 +0,0 @@
|
||||||
#!/bin/bash
|
|
||||||
|
|
||||||
num=$1
|
|
||||||
|
|
||||||
echo "$num" | grep -q "^[1-9][0-9]\{,4\}$" || {
|
|
||||||
echo "Err: no valid number given" >&2
|
|
||||||
exit 1
|
|
||||||
}
|
|
||||||
|
|
||||||
parent=$((num / 100))
|
|
||||||
pdir="solutions/${parent}/q${num}"
|
|
||||||
sol_file="${pdir}/solution.go"
|
|
||||||
|
|
||||||
if [ -f "$sol_file" ]; then
|
|
||||||
exit 0
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "Creating template for question No. $num" >&2
|
|
||||||
mkdir -pv "$pdir"
|
|
||||||
echo "package q$num" > "$sol_file"
|
|
||||||
echo "Created $sol_file"
|
|
||||||
12
go.mod
12
go.mod
|
|
@ -1,15 +1,3 @@
|
||||||
module leetcode-go
|
module leetcode-go
|
||||||
|
|
||||||
go 1.25.5
|
go 1.25.5
|
||||||
|
|
||||||
require (
|
|
||||||
github.com/emirpasic/gods/v2 v2.0.0-alpha
|
|
||||||
github.com/k0kubun/pp/v3 v3.5.0
|
|
||||||
)
|
|
||||||
|
|
||||||
require (
|
|
||||||
github.com/mattn/go-colorable v0.1.14 // indirect
|
|
||||||
github.com/mattn/go-isatty v0.0.20 // indirect
|
|
||||||
golang.org/x/sys v0.29.0 // indirect
|
|
||||||
golang.org/x/text v0.26.0 // indirect
|
|
||||||
)
|
|
||||||
|
|
|
||||||
13
go.sum
13
go.sum
|
|
@ -1,13 +0,0 @@
|
||||||
github.com/emirpasic/gods/v2 v2.0.0-alpha h1:dwFlh8pBg1VMOXWGipNMRt8v96dKAIvBehtCt6OtunU=
|
|
||||||
github.com/emirpasic/gods/v2 v2.0.0-alpha/go.mod h1:W0y4M2dtBB9U5z3YlghmpuUhiaZT2h6yoeE+C1sCp6A=
|
|
||||||
github.com/k0kubun/pp/v3 v3.5.0 h1:iYNlYA5HJAJvkD4ibuf9c8y6SHM0QFhaBuCqm1zHp0w=
|
|
||||||
github.com/k0kubun/pp/v3 v3.5.0/go.mod h1:5lzno5ZZeEeTV/Ky6vs3g6d1U3WarDrH8k240vMtGro=
|
|
||||||
github.com/mattn/go-colorable v0.1.14 h1:9A9LHSqF/7dyVVX6g0U9cwm9pG3kP9gSzcuIPHPsaIE=
|
|
||||||
github.com/mattn/go-colorable v0.1.14/go.mod h1:6LmQG8QLFO4G5z1gPvYEzlUgJ2wF+stgPZH1UqBm1s8=
|
|
||||||
github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
|
|
||||||
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
|
|
||||||
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
|
||||||
golang.org/x/sys v0.29.0 h1:TPYlXGxvx1MGTn2GiZDhnjPA9wZzZeGKHHmKhHYvgaU=
|
|
||||||
golang.org/x/sys v0.29.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
|
|
||||||
golang.org/x/text v0.26.0 h1:P42AVeLghgTYr4+xUnTRKDMqpar+PtX7KWuNQL21L8M=
|
|
||||||
golang.org/x/text v0.26.0/go.mod h1:QK15LZJUUQVJxhz7wXgxSy/CJaTFjd0G+YLonydOVQA=
|
|
||||||
|
|
@ -1,65 +0,0 @@
|
||||||
package q15
|
|
||||||
|
|
||||||
import "slices"
|
|
||||||
|
|
||||||
func sortAndDedup3(nums []int) []int {
|
|
||||||
slices.Sort(nums)
|
|
||||||
head, dup := 0, 0
|
|
||||||
for i := 1; i < len(nums); i++ {
|
|
||||||
if nums[i] == nums[head] {
|
|
||||||
dup++
|
|
||||||
} else {
|
|
||||||
dup = 0
|
|
||||||
}
|
|
||||||
if dup < 3 {
|
|
||||||
head++
|
|
||||||
nums[head] = nums[i]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return nums[:head+1]
|
|
||||||
}
|
|
||||||
|
|
||||||
func threeSum(nums []int) [][]int {
|
|
||||||
nums = sortAndDedup3(nums)
|
|
||||||
ret := [][]int{}
|
|
||||||
|
|
||||||
appendResult := func(a, b, c int) {
|
|
||||||
triplet := []int{a, b, c}
|
|
||||||
if len(ret) > 0 && slices.Equal(triplet, ret[len(ret)-1]) {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
ret = append(ret, triplet)
|
|
||||||
}
|
|
||||||
|
|
||||||
for i := 0; i < len(nums)-2; i++ {
|
|
||||||
if nums[i] > 0 {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
wants := -nums[i]
|
|
||||||
l, r := i+1, len(nums)-1
|
|
||||||
for l < r {
|
|
||||||
for l < r && nums[l]+nums[r] > wants {
|
|
||||||
r--
|
|
||||||
}
|
|
||||||
if l < r && nums[l]+nums[r] == wants {
|
|
||||||
appendResult(nums[i], nums[l], nums[r])
|
|
||||||
r--
|
|
||||||
}
|
|
||||||
for l < r && nums[l]+nums[r] < wants {
|
|
||||||
l++
|
|
||||||
}
|
|
||||||
if l < r && nums[l]+nums[r] == wants {
|
|
||||||
appendResult(nums[i], nums[l], nums[r])
|
|
||||||
l++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// skip same numbers
|
|
||||||
for ; i < len(nums)-2 && nums[i] == nums[i+1]; i++ {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = threeSum
|
|
||||||
|
|
@ -1,39 +0,0 @@
|
||||||
package q17
|
|
||||||
|
|
||||||
var alphabets = [][]byte{
|
|
||||||
[]byte("abc"),
|
|
||||||
[]byte("def"),
|
|
||||||
[]byte("ghi"),
|
|
||||||
[]byte("jkl"),
|
|
||||||
[]byte("mno"),
|
|
||||||
[]byte("pqrs"),
|
|
||||||
[]byte("tuv"),
|
|
||||||
[]byte("wxyz"),
|
|
||||||
}
|
|
||||||
|
|
||||||
func combinations(offsets []int, i int, buffer []byte, strings []string) []string {
|
|
||||||
if buffer == nil {
|
|
||||||
buffer = make([]byte, len(offsets))
|
|
||||||
}
|
|
||||||
|
|
||||||
if i == len(offsets) {
|
|
||||||
return append(strings, string(buffer))
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, c := range alphabets[offsets[i]] {
|
|
||||||
buffer[i] = c
|
|
||||||
strings = combinations(offsets, i+1, buffer, strings)
|
|
||||||
}
|
|
||||||
return strings
|
|
||||||
}
|
|
||||||
|
|
||||||
func letterCombinations(digits string) []string {
|
|
||||||
offsets := make([]int, len(digits))
|
|
||||||
for i := range len(digits) {
|
|
||||||
offsets[i] = int(digits[i] - '2')
|
|
||||||
}
|
|
||||||
|
|
||||||
return combinations(offsets, 0, nil, []string{})
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = letterCombinations
|
|
||||||
|
|
@ -1,32 +0,0 @@
|
||||||
package q20
|
|
||||||
|
|
||||||
func isValid(s string) bool {
|
|
||||||
stack := make([]byte, 0, len(s)/2)
|
|
||||||
|
|
||||||
for i := range len(s) {
|
|
||||||
switch s[i] {
|
|
||||||
case '(', '[', '{':
|
|
||||||
stack = append(stack, s[i])
|
|
||||||
case ')':
|
|
||||||
if len(stack) == 0 || stack[len(stack)-1] != '(' {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
stack = stack[:len(stack)-1]
|
|
||||||
|
|
||||||
case ']':
|
|
||||||
if len(stack) == 0 || stack[len(stack)-1] != '[' {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
stack = stack[:len(stack)-1]
|
|
||||||
|
|
||||||
case '}':
|
|
||||||
if len(stack) == 0 || stack[len(stack)-1] != '{' {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
stack = stack[:len(stack)-1]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return len(stack) == 0
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = isValid
|
|
||||||
|
|
@ -1,19 +0,0 @@
|
||||||
package q35
|
|
||||||
|
|
||||||
func searchInsert(nums []int, target int) int {
|
|
||||||
l, r := 0, len(nums)
|
|
||||||
for l < r {
|
|
||||||
mid := (l + r) / 2
|
|
||||||
switch {
|
|
||||||
case nums[mid] == target:
|
|
||||||
return mid
|
|
||||||
case nums[mid] > target:
|
|
||||||
r = mid
|
|
||||||
default:
|
|
||||||
l = mid + 1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return l
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = searchInsert
|
|
||||||
|
|
@ -1,18 +0,0 @@
|
||||||
package q53
|
|
||||||
|
|
||||||
import "math"
|
|
||||||
|
|
||||||
func maxSubArray(nums []int) int {
|
|
||||||
sum := 0
|
|
||||||
minSubstract := 0
|
|
||||||
maxSubArr := math.MinInt
|
|
||||||
for i := range nums {
|
|
||||||
sum += nums[i]
|
|
||||||
nums[i] = sum
|
|
||||||
maxSubArr = max(maxSubArr, nums[i]-minSubstract)
|
|
||||||
minSubstract = min(minSubstract, nums[i])
|
|
||||||
}
|
|
||||||
return maxSubArr
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = maxSubArray
|
|
||||||
|
|
@ -1,22 +0,0 @@
|
||||||
package q66
|
|
||||||
|
|
||||||
func plusOne(digits []int) []int {
|
|
||||||
digits[len(digits)-1]++
|
|
||||||
for i := len(digits) - 1; i > 0; i-- {
|
|
||||||
if digits[i] > 9 {
|
|
||||||
digits[i] -= 10
|
|
||||||
digits[i-1]++
|
|
||||||
} else {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if digits[0] > 9 {
|
|
||||||
digits[0] -= 10
|
|
||||||
ret := make([]int, 0, len(digits)+1)
|
|
||||||
ret = append(ret, 1)
|
|
||||||
return append(ret, digits...)
|
|
||||||
}
|
|
||||||
return digits
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = plusOne
|
|
||||||
|
|
@ -1,28 +0,0 @@
|
||||||
package q67
|
|
||||||
|
|
||||||
func toDigit(byt byte) uint8 { return byt - '0' }
|
|
||||||
func toByte(digit uint8) byte { return '0' + digit }
|
|
||||||
|
|
||||||
func addBinary(a string, b string) string {
|
|
||||||
lenA, lenB := len(a), len(b)
|
|
||||||
ret := make([]byte, max(lenA, lenB)+1)
|
|
||||||
var carry uint8
|
|
||||||
for i := range ret {
|
|
||||||
d := carry
|
|
||||||
if i < lenA {
|
|
||||||
d += toDigit(a[lenA-i-1])
|
|
||||||
}
|
|
||||||
if i < lenB {
|
|
||||||
d += toDigit(b[lenB-i-1])
|
|
||||||
}
|
|
||||||
carry = d / 2
|
|
||||||
ret[len(ret)-i-1] = toByte(d % 2)
|
|
||||||
}
|
|
||||||
|
|
||||||
if ret[0] != '1' {
|
|
||||||
return string(ret[1:])
|
|
||||||
}
|
|
||||||
return string(ret)
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = addBinary
|
|
||||||
|
|
@ -1,26 +0,0 @@
|
||||||
package q69
|
|
||||||
|
|
||||||
func mySqrt(x int) int {
|
|
||||||
if x < 2 {
|
|
||||||
return x
|
|
||||||
}
|
|
||||||
l, r := 0, x/2+1
|
|
||||||
for l < r {
|
|
||||||
m := (l + r) / 2
|
|
||||||
sq := m * m
|
|
||||||
switch {
|
|
||||||
case sq == x:
|
|
||||||
return m
|
|
||||||
case sq < x:
|
|
||||||
if (m+1)*(m+1) > x {
|
|
||||||
return m
|
|
||||||
}
|
|
||||||
l = m + 1
|
|
||||||
case sq > x:
|
|
||||||
r = m
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return -1
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = mySqrt
|
|
||||||
|
|
@ -1,24 +0,0 @@
|
||||||
package q70
|
|
||||||
|
|
||||||
func nWays(n, i int, cache []int) int {
|
|
||||||
if i == n {
|
|
||||||
return 1
|
|
||||||
}
|
|
||||||
if i > n {
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
if cache == nil {
|
|
||||||
cache = make([]int, n)
|
|
||||||
} else if cache[i] != 0 {
|
|
||||||
return cache[i]
|
|
||||||
}
|
|
||||||
ret := nWays(n, i+1, cache) + nWays(n, i+2, cache)
|
|
||||||
cache[i] = ret
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
func climbStairs(n int) int {
|
|
||||||
return nWays(n, 0, nil)
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = climbStairs
|
|
||||||
|
|
@ -1,18 +0,0 @@
|
||||||
package q9
|
|
||||||
|
|
||||||
import "strconv"
|
|
||||||
|
|
||||||
func isPalindrome(x int) bool {
|
|
||||||
if x < 0 {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
str := strconv.FormatInt(int64(x), 10)
|
|
||||||
for i := range len(str) / 2 {
|
|
||||||
if str[i] != str[len(str)-1-i] {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = isPalindrome
|
|
||||||
|
|
@ -1,20 +0,0 @@
|
||||||
package q104
|
|
||||||
|
|
||||||
type TreeNode struct {
|
|
||||||
Val int
|
|
||||||
Left *TreeNode
|
|
||||||
Right *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func md(d int, node *TreeNode) int {
|
|
||||||
if node == nil {
|
|
||||||
return d - 1
|
|
||||||
}
|
|
||||||
return max(md(d+1, node.Left), md(d+1, node.Right))
|
|
||||||
}
|
|
||||||
|
|
||||||
func maxDepth(root *TreeNode) int {
|
|
||||||
return md(1, root)
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = maxDepth
|
|
||||||
|
|
@ -1,26 +0,0 @@
|
||||||
package q108
|
|
||||||
|
|
||||||
type TreeNode struct {
|
|
||||||
Val int
|
|
||||||
Left *TreeNode
|
|
||||||
Right *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func sortedArrayToBST(nums []int) *TreeNode {
|
|
||||||
if len(nums) == 0 {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
if len(nums) == 1 {
|
|
||||||
return &TreeNode{Val: nums[0]}
|
|
||||||
}
|
|
||||||
|
|
||||||
l, r := nums[:len(nums)/2], nums[len(nums)/2+1:]
|
|
||||||
m := nums[len(nums)/2]
|
|
||||||
return &TreeNode{
|
|
||||||
Val: m,
|
|
||||||
Left: sortedArrayToBST(l),
|
|
||||||
Right: sortedArrayToBST(r),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = sortedArrayToBST
|
|
||||||
|
|
@ -1,14 +0,0 @@
|
||||||
package q120
|
|
||||||
|
|
||||||
func minimumTotal(triangle [][]int) int {
|
|
||||||
size := len(triangle)
|
|
||||||
|
|
||||||
for row := size - 2; row >= 0; row-- {
|
|
||||||
for i := range triangle[row] {
|
|
||||||
triangle[row][i] += min(triangle[row+1][i], triangle[row+1][i+1])
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return triangle[0][0]
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = minimumTotal
|
|
||||||
|
|
@ -1,11 +0,0 @@
|
||||||
package q136
|
|
||||||
|
|
||||||
func singleNumber(nums []int) int {
|
|
||||||
x := 0
|
|
||||||
for _, num := range nums {
|
|
||||||
x ^= num
|
|
||||||
}
|
|
||||||
return x
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = singleNumber
|
|
||||||
|
|
@ -1,28 +0,0 @@
|
||||||
package q141
|
|
||||||
|
|
||||||
type ListNode struct {
|
|
||||||
Val int
|
|
||||||
Next *ListNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func hasCycle(head *ListNode) bool {
|
|
||||||
if head == nil {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
p1, p2 := head, head
|
|
||||||
for {
|
|
||||||
for range 2 {
|
|
||||||
p2 = p2.Next
|
|
||||||
switch p2 {
|
|
||||||
case nil:
|
|
||||||
return false
|
|
||||||
case p1:
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
p1 = p1.Next
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = hasCycle
|
|
||||||
|
|
@ -1,13 +0,0 @@
|
||||||
package q190
|
|
||||||
|
|
||||||
func reverseBits(n int) int {
|
|
||||||
ret := 0
|
|
||||||
for i := range 32 {
|
|
||||||
if n|(1<<i) == n {
|
|
||||||
ret |= 1 << (31 - i)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = reverseBits
|
|
||||||
|
|
@ -1,13 +0,0 @@
|
||||||
package q191
|
|
||||||
|
|
||||||
func hammingWeight(n int) int {
|
|
||||||
num := 0
|
|
||||||
for ; n > 0; n >>= 1 {
|
|
||||||
if n|1 == n {
|
|
||||||
num++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return num
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = hammingWeight
|
|
||||||
|
|
@ -1,37 +0,0 @@
|
||||||
package q199
|
|
||||||
|
|
||||||
type TreeNode struct {
|
|
||||||
Val int
|
|
||||||
Left *TreeNode
|
|
||||||
Right *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func rightSideView(root *TreeNode) []int {
|
|
||||||
ret := []int{}
|
|
||||||
|
|
||||||
type qElem struct {
|
|
||||||
height int
|
|
||||||
node *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
queue := []qElem{{0, root}}
|
|
||||||
var last *qElem
|
|
||||||
for ; len(queue) > 0; queue = queue[1:] {
|
|
||||||
cur := &queue[0]
|
|
||||||
if cur.node == nil {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
if last != nil && last.height < cur.height {
|
|
||||||
ret = append(ret, last.node.Val)
|
|
||||||
}
|
|
||||||
last = cur
|
|
||||||
queue = append(queue, qElem{cur.height + 1, cur.node.Left}, qElem{cur.height + 1, cur.node.Right})
|
|
||||||
}
|
|
||||||
if last != nil {
|
|
||||||
ret = append(ret, last.node.Val)
|
|
||||||
}
|
|
||||||
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = rightSideView
|
|
||||||
|
|
@ -1,31 +0,0 @@
|
||||||
package q200
|
|
||||||
|
|
||||||
const (
|
|
||||||
VISITED byte = '.'
|
|
||||||
LAND byte = '1'
|
|
||||||
)
|
|
||||||
|
|
||||||
func traverse(grid [][]byte, x, y int) int {
|
|
||||||
if x < 0 || y < 0 || x >= len(grid[0]) || y >= len(grid) || grid[y][x] != LAND {
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
|
|
||||||
grid[y][x] = VISITED
|
|
||||||
traverse(grid, x+1, y)
|
|
||||||
traverse(grid, x-1, y)
|
|
||||||
traverse(grid, x, y+1)
|
|
||||||
traverse(grid, x, y-1)
|
|
||||||
return 1
|
|
||||||
}
|
|
||||||
|
|
||||||
func numIslands(grid [][]byte) int {
|
|
||||||
count := 0
|
|
||||||
for y := range grid {
|
|
||||||
for x := range grid[y] {
|
|
||||||
count += traverse(grid, x, y)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return count
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = numIslands
|
|
||||||
|
|
@ -1,105 +0,0 @@
|
||||||
package q208
|
|
||||||
|
|
||||||
type tNode struct {
|
|
||||||
str string
|
|
||||||
childs [26]*tNode
|
|
||||||
hasWord bool
|
|
||||||
}
|
|
||||||
|
|
||||||
func (n *tNode) index() int { return index(n.str) }
|
|
||||||
|
|
||||||
func (n *tNode) split(prefixLen int) (*tNode, *tNode) {
|
|
||||||
if len(n.str) < prefixLen {
|
|
||||||
panic("cannot split node")
|
|
||||||
}
|
|
||||||
if len(n.str) == prefixLen {
|
|
||||||
return n, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
prefix := n.str[:prefixLen]
|
|
||||||
n.str = n.str[prefixLen:]
|
|
||||||
p := &tNode{str: prefix}
|
|
||||||
p.childs[n.index()] = n
|
|
||||||
return p, n
|
|
||||||
}
|
|
||||||
|
|
||||||
func commonPrefix(a, b string) int {
|
|
||||||
minLen := min(len(a), len(b))
|
|
||||||
for i := range minLen {
|
|
||||||
if a[i] != b[i] {
|
|
||||||
return i
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return minLen
|
|
||||||
}
|
|
||||||
|
|
||||||
func index(str string) int {
|
|
||||||
if len(str) > 0 {
|
|
||||||
return int(str[0] - 'a')
|
|
||||||
}
|
|
||||||
return -1 // root
|
|
||||||
}
|
|
||||||
|
|
||||||
type Trie struct {
|
|
||||||
root *tNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func Constructor() Trie {
|
|
||||||
return Trie{
|
|
||||||
root: &tNode{},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (t *Trie) Insert(word string) {
|
|
||||||
node := t.root
|
|
||||||
for len(word) > 0 {
|
|
||||||
idx := index(word)
|
|
||||||
next := node.childs[idx]
|
|
||||||
if next != nil {
|
|
||||||
pflen := commonPrefix(word, next.str)
|
|
||||||
next, _ = next.split(pflen)
|
|
||||||
node.childs[next.index()] = next
|
|
||||||
word = word[pflen:]
|
|
||||||
} else {
|
|
||||||
next = &tNode{str: word}
|
|
||||||
word = ""
|
|
||||||
node.childs[idx] = next
|
|
||||||
}
|
|
||||||
node = next
|
|
||||||
}
|
|
||||||
node.hasWord = true
|
|
||||||
}
|
|
||||||
|
|
||||||
func (t *Trie) Search(word string) bool {
|
|
||||||
node := t.root
|
|
||||||
for len(word) > 0 {
|
|
||||||
next := node.childs[index(word)]
|
|
||||||
if next == nil {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
pflen := commonPrefix(word, next.str)
|
|
||||||
if pflen != len(next.str) {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
word = word[pflen:]
|
|
||||||
node = next
|
|
||||||
}
|
|
||||||
return node.hasWord
|
|
||||||
}
|
|
||||||
|
|
||||||
func (t *Trie) StartsWith(prefix string) bool {
|
|
||||||
node := t.root
|
|
||||||
for len(prefix) > 0 {
|
|
||||||
next := node.childs[index(prefix)]
|
|
||||||
if next == nil {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
pflen := commonPrefix(prefix, next.str)
|
|
||||||
if pflen != len(next.str) && pflen != len(prefix) {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
prefix = prefix[pflen:]
|
|
||||||
node = next
|
|
||||||
}
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
|
|
@ -1,37 +0,0 @@
|
||||||
package q215
|
|
||||||
|
|
||||||
func findKthLargest(nums []int, k int) int {
|
|
||||||
// build max-heap
|
|
||||||
for i := 1; i < len(nums); i++ {
|
|
||||||
for j := i; j > 0; j = (j - 1) / 2 {
|
|
||||||
parent := (j - 1) / 2
|
|
||||||
if nums[j] > nums[parent] {
|
|
||||||
nums[j], nums[parent] = nums[parent], nums[j]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for range k - 1 {
|
|
||||||
// pop the heap
|
|
||||||
nums[0] = nums[len(nums)-1]
|
|
||||||
nums = nums[:len(nums)-1]
|
|
||||||
|
|
||||||
i := 0
|
|
||||||
for i*2+1 < len(nums) {
|
|
||||||
l, r := i*2+1, i*2+2
|
|
||||||
next := l
|
|
||||||
if r < len(nums) && nums[r] > nums[l] {
|
|
||||||
next = r
|
|
||||||
}
|
|
||||||
if nums[i] >= nums[next] {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
nums[i], nums[next] = nums[next], nums[i]
|
|
||||||
i = next
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nums[0]
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = findKthLargest
|
|
||||||
|
|
@ -1,32 +0,0 @@
|
||||||
package q228
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
"strconv"
|
|
||||||
)
|
|
||||||
|
|
||||||
func addToRanges(output []string, a, b int) []string {
|
|
||||||
if a == b {
|
|
||||||
return append(output, strconv.FormatInt(int64(a), 10))
|
|
||||||
}
|
|
||||||
return append(output, fmt.Sprintf("%d->%d", a, b))
|
|
||||||
}
|
|
||||||
|
|
||||||
func summaryRanges(nums []int) []string {
|
|
||||||
if len(nums) == 0 {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
output := []string{}
|
|
||||||
l := 0
|
|
||||||
for r := 1; r < len(nums); r++ {
|
|
||||||
if nums[r]-nums[r-1] != 1 {
|
|
||||||
output = addToRanges(output, nums[l], nums[r-1])
|
|
||||||
l = r
|
|
||||||
}
|
|
||||||
}
|
|
||||||
output = addToRanges(output, nums[l], nums[len(nums)-1])
|
|
||||||
return output
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = summaryRanges
|
|
||||||
|
|
@ -1,29 +0,0 @@
|
||||||
package q2483
|
|
||||||
|
|
||||||
func bestClosingTime(customers string) int {
|
|
||||||
numY := 0
|
|
||||||
for i := range len(customers) {
|
|
||||||
if customers[i] == 'Y' {
|
|
||||||
numY++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
minCloseHour := 0
|
|
||||||
minPenalty := numY
|
|
||||||
penalty := numY
|
|
||||||
for i := range len(customers) {
|
|
||||||
// close at (i + 1)th hour
|
|
||||||
switch customers[i] {
|
|
||||||
case 'N':
|
|
||||||
penalty++
|
|
||||||
case 'Y':
|
|
||||||
penalty--
|
|
||||||
}
|
|
||||||
if penalty < minPenalty {
|
|
||||||
minPenalty = penalty
|
|
||||||
minCloseHour = i + 1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return minCloseHour
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = bestClosingTime
|
|
||||||
|
|
@ -1,25 +0,0 @@
|
||||||
package q383
|
|
||||||
|
|
||||||
func canConstruct(ransomNote string, magazine string) bool {
|
|
||||||
counts := make([]int, 'z'-'a'+1)
|
|
||||||
|
|
||||||
for _, c := range magazine {
|
|
||||||
if c < 'a' || c > 'z' {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
counts[int(c)-int('a')]++
|
|
||||||
}
|
|
||||||
for _, c := range ransomNote {
|
|
||||||
if c < 'a' || c > 'z' {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
offset := int(c) - int('a')
|
|
||||||
counts[offset]--
|
|
||||||
if counts[offset] < 0 {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = canConstruct
|
|
||||||
|
|
@ -1,14 +0,0 @@
|
||||||
package q3075
|
|
||||||
|
|
||||||
import "slices"
|
|
||||||
|
|
||||||
func maximumHappinessSum(happiness []int, k int) int64 {
|
|
||||||
slices.Sort(happiness)
|
|
||||||
var sum int64
|
|
||||||
for i := range k {
|
|
||||||
sum += max(0, int64(happiness[len(happiness)-1-i]-i))
|
|
||||||
}
|
|
||||||
return sum
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = maximumHappinessSum
|
|
||||||
|
|
@ -1,37 +0,0 @@
|
||||||
package q530
|
|
||||||
|
|
||||||
import "math"
|
|
||||||
|
|
||||||
type TreeNode struct {
|
|
||||||
Val int
|
|
||||||
Left *TreeNode
|
|
||||||
Right *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func getMinimumDifference(root *TreeNode) int {
|
|
||||||
minDiff := math.MaxInt
|
|
||||||
var last *int
|
|
||||||
|
|
||||||
var check = func(num int) {
|
|
||||||
if last == nil {
|
|
||||||
last = &num
|
|
||||||
return
|
|
||||||
}
|
|
||||||
minDiff = min(minDiff, num-*last)
|
|
||||||
*last = num
|
|
||||||
}
|
|
||||||
var traverse func(node *TreeNode)
|
|
||||||
traverse = func(node *TreeNode) {
|
|
||||||
if node == nil {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
traverse(node.Left)
|
|
||||||
check(node.Val)
|
|
||||||
traverse(node.Right)
|
|
||||||
}
|
|
||||||
traverse(root)
|
|
||||||
|
|
||||||
return minDiff
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = getMinimumDifference
|
|
||||||
|
|
@ -1,43 +0,0 @@
|
||||||
package q637
|
|
||||||
|
|
||||||
type TreeNode struct {
|
|
||||||
Val int
|
|
||||||
Left *TreeNode
|
|
||||||
Right *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
func averageOfLevels(root *TreeNode) []float64 {
|
|
||||||
type qElem struct {
|
|
||||||
level int
|
|
||||||
node *TreeNode
|
|
||||||
}
|
|
||||||
|
|
||||||
ret := []float64{}
|
|
||||||
level := 0
|
|
||||||
n := 0 // number of nodes
|
|
||||||
var sum float64
|
|
||||||
|
|
||||||
queue := []qElem{{level: 0, node: root}}
|
|
||||||
for ; len(queue) > 0; queue = queue[1:] {
|
|
||||||
curr := &queue[0]
|
|
||||||
if curr.level == level {
|
|
||||||
sum += float64(curr.node.Val)
|
|
||||||
n++
|
|
||||||
} else {
|
|
||||||
ret = append(ret, sum/float64(n))
|
|
||||||
sum = float64(curr.node.Val)
|
|
||||||
n = 1
|
|
||||||
level = curr.level
|
|
||||||
}
|
|
||||||
if curr.node.Left != nil {
|
|
||||||
queue = append(queue, qElem{curr.level + 1, curr.node.Left})
|
|
||||||
}
|
|
||||||
if curr.node.Right != nil {
|
|
||||||
queue = append(queue, qElem{curr.level + 1, curr.node.Right})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
ret = append(ret, sum/float64(n))
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = averageOfLevels
|
|
||||||
|
|
@ -1,50 +0,0 @@
|
||||||
package q909
|
|
||||||
|
|
||||||
func coord(n, num int) (x, y int) {
|
|
||||||
num -= 1
|
|
||||||
row := num / n
|
|
||||||
y = n - row - 1
|
|
||||||
x = num % n
|
|
||||||
if row%2 == 1 {
|
|
||||||
x = n - 1 - x
|
|
||||||
}
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
func snakesAndLadders(board [][]int) int {
|
|
||||||
n, sqN := len(board), len(board)*len(board)
|
|
||||||
leastRolls := make([]int, sqN)
|
|
||||||
if len(leastRolls) == 1 {
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
|
|
||||||
queue := make([]int, 0, sqN)
|
|
||||||
queue = append(queue, 1)
|
|
||||||
for ; len(queue) > 0; queue = queue[1:] {
|
|
||||||
cur := queue[0]
|
|
||||||
for dist := 1; dist <= 6 && cur+dist <= sqN; dist++ {
|
|
||||||
next := cur + dist
|
|
||||||
x, y := coord(n, next)
|
|
||||||
if board[y][x] != -1 {
|
|
||||||
next = board[y][x]
|
|
||||||
}
|
|
||||||
rolls := leastRolls[cur-1] + 1
|
|
||||||
|
|
||||||
if (next > 1 && leastRolls[next-1] == 0) || rolls < leastRolls[next-1] {
|
|
||||||
leastRolls[next-1] = rolls
|
|
||||||
if next == sqN {
|
|
||||||
return rolls
|
|
||||||
}
|
|
||||||
queue = append(queue, next)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
l := leastRolls[sqN-1]
|
|
||||||
if l == 0 {
|
|
||||||
return -1
|
|
||||||
}
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ = snakesAndLadders
|
|
||||||
6
tools.go
6
tools.go
|
|
@ -1,6 +0,0 @@
|
||||||
package leetcodego
|
|
||||||
|
|
||||||
import (
|
|
||||||
_ "github.com/emirpasic/gods/v2/utils"
|
|
||||||
_ "github.com/k0kubun/pp/v3"
|
|
||||||
)
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue