zoukankan      html  css  js  c++  java
  • LeetCode Golang 2. 两数相加

    2. 两数相加

    给出两个 非空 的链表用来表示两个非负的整数。其中,它们各自的位数是按照 逆序 的方式存储的,并且它们的每个节点只能存储 一位 数字。

    如果,我们将这两个数相加起来,则会返回一个新的链表来表示它们的和。

    您可以假设除了数字 0 之外,这两个数都不会以 0 开头。

    示例:

    输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)
    输出:7 -> 0 -> 8
    原因:342 + 465 = 807

    错误解法:

    错误思路: 将数字读出来还原, 进行加法得到sum, 再拆分sum写入到新的链表中

    错误原因: 大数字会导致内存溢出

    func addTwoNumbers(l1 *ListNode, l2 *ListNode) *ListNode {
    	if l1 == nil || l2 == nil {
    		return nil
    	}
    	l := new(ListNode)
    	rst := l
    
    	pow10 := func(a int) int {
    		if a == 0 {
    			return 1
    		}
    		rst := 1
    		for i := 1; i <= a; i++ {
    			rst *= 10
    		}
    		return rst
    	}
    
    	getInt := func(l *ListNode) (int) {
    		if l == nil {
    			return 0
    		}
    		nums := []int{}
    		for l != nil {
    			nums = append(nums, l.Val)
    			l = l.Next
    		}
    		rst := 0
    		for k, v := range nums {
    			rst += pow10(k) * v
    		}
    		return rst
    	}
    
    	rstNum := getInt(l1) + getInt(l2)
    	rstArr := strconv.Itoa(rstNum)
    	bits := len(rstArr)
    	for i := 1; i <= bits; i++ {
    		l.Val = rstNum / pow10(i-1) % 10
    		if i == bits {
    			break
    		}
    		l.Next = new(ListNode)
    		l = l.Next
    	}
    	return rst
    }
    

    正确解法:

    思路: 直接模拟加法过程

    package main
    
    import "fmt"
    
    type ListNode struct {
    	Val  int
    	Next *ListNode
    }
    
    /*
    输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)
    输出:7 -> 0 -> 8
    原因:342 + 465 = 807
    */
    
    //[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1]
    //[5,6,4]
    
    func main() {
    	l1 := new(ListNode)
    	l2 := new(ListNode)
    	tmp1 := l1
    	tmp2 := l2
    	nums1 := []int{3, 5, 2}
    	nums2 := []int{5,6,4}
    
    	for i := 0; i < len(nums1); i++ {
    		tmp1.Val = nums1[i]
    		if i == len(nums1)-1 {
    			break
    		}
    		tmp1.Next = new(ListNode)
    		tmp1 = tmp1.Next
    	}
    	for i := 0; i < len(nums2); i++ {
    		tmp2.Val = nums2[i]
    		if i == len(nums2)-1 {
    			break
    		}
    		tmp2.Next = new(ListNode)
    		tmp2 = tmp2.Next
    	}
    
    	fmt.Println(l2.getInt())
    	fmt.Println(l1.getInt())
    	l2 = addTwoNumbers(l1, l2)
    	fmt.Println(l2.getInt())
    
    }
    
    func addTwoNumbers(l1 *ListNode, l2 *ListNode) *ListNode {
    	if l1 == nil || l2 == nil {
    		return nil
    	}
    
    	l := new(ListNode)
    	l.Val = 0
    	tmp := l
    	flag := 0 // flag标志位, 模拟加法中的进位加1
    
    	for {
    		num := l1.Val + l2.Val + tmp.Val
    		if num >= 10 {
    			tmp.Val = num % 10
    			flag = 1
    		} else {
    			tmp.Val = num
    		}
    
    		if l1.Next == nil && l2.Next == nil {
    			break
    		}
    		l1 = l1.Next
    		l2 = l2.Next
    		if l1 == nil {
    			l1 = new(ListNode)
    			l1.Val = 0
    		}
    		if l2 == nil {
    			l2 = new(ListNode)
    			l2.Val = 0
    		}
    
    		tmp.Next = new(ListNode)
    		if flag == 1 {
    			tmp.Next.Val = 1
    			flag = 0
    		} else {
    			tmp.Next.Val = 0
    		}
    		tmp = tmp.Next
    	}
    	if flag == 1 { // 这个判断一定要加, 因为 5 + 5 返回 0,1
    		tmp.Next = new(ListNode)
    		tmp.Next.Val = 1
    	}
    
    	return l
    }
    
    func (l *ListNode) Length() int {
    	if l == nil {
    		return 0
    	}
    	i := 0
    	for l != nil {
    		l = l.Next
    		i++
    	}
    	return i
    }
    
    // 返回链表中的值
    func (l *ListNode) getInt() (int) {
    	if l == nil {
    		return 0
    	}
    	nums := []int{}
    	for l != nil {
    		nums = append(nums, l.Val)
    		l = l.Next
    	}
    	rst := 0
    	for k, v := range nums {
    		rst += pow10(k) * v
    	}
    	return rst
    }
    
    // 返回10的几次方 <---- 大数字的情况下在这里首先溢出, 写在这里只为了测试用
    func pow10(a int) int {
    	if a == 0 {
    		return 1
    	}
    	rst := 1
    	for i := 1; i <= a; i++ {
    		rst *= 10
    	}
    	return rst
    }
    

     

    /* 字体问题: 有些分不清 l 和 1,建议复制到IDE中进行查看 */

  • 相关阅读:
    asp.net的decimal保留两位小数
    由于管理员设置的策略,该磁盘处于脱机状态-Win 2008 R2
    论大公司的通病和缺点
    sql server删除数据后空间无变化处理方法
    sql server压缩数据库和日志文件
    SQL千万级数据设计和优化
    SQL Server索引怎么用
    在电脑上测试手机网站
    asp.net实现GZip压缩和GZip解压
    WebService教程和分析
  • 原文地址:https://www.cnblogs.com/gettolive/p/10169276.html
Copyright © 2011-2022 走看看