Leetcode1071. 字符串的最大公因子(三种方法,带详细解析)

Leetcode1071. 字符串的最大公因子

对于字符串 s 和 t,只有在 s = t + ... + t(t 自身连接 1 次或多次)时,我们才认定 "t 能除尽 s"。

给定两个字符串 str1 和 str2 。返回 最长字符串 x,要求满足 x 能除尽 str1 且 x 能除尽 str2 。


示例 1:

输入:str1 = "ABCABC", str2 = "ABC"

输出:"ABC"


示例 2:

输入:str1 = "ABABAB", str2 = "ABAB"

输出:"AB"

示例 3:


输入:str1 = "LEET", str2 = "CODE"

输出:""


提示:

1 <= str1.length, str2.length <= 1000

str1 和 str2 由大写英文字母组成

方法一:最大公因子法

分析:

  1. 如果两个字符串有最大公因子那么str1+str2和str2+str1一定是一样的
    比如例一:str1 = "ABCABC", str2 = "ABC" str1+str2 和 str2+str1 都是"ABCABCABC"
    如果两个字符串没有最大公因子那么str1+str2和str2+str1一定不一样
  2. 如果两个字符串有最大公因子那么str1,str2他们的长度一定符合辗转相除法,我们可以通过两个字符串的长度,计算出他们最大公因子的长度
    比如例一中str1的长度为6,str2的长度为3,6和3的最大公因数是3,输出的结果长度恰好是3
  3. 然后通过计算出来的长度使用substring()截取出来即可
javascript 复制代码
	var gcdOfStrings = function (str1, str2) {
	    if (str1 + str2 !== str2 + str1) return '' // 如果不满足最大公因子的条件直接返回空字符串
	    const gcd = (a, b) => (a % b == 0 ? b : gcd(b, a % b))//辗转相除法
	    return str1.substring(0, gcd(str1.length, str2.length))
	};

运行结果

方法二:暴力

这个效率比较慢,主要是针对不满足条件的情况会比较浪费时间,当然可以在前面加一个不满足条件的直接返回空来解决这个效率慢的问题

源码版

javascript 复制代码
var gcdOfStrings = function (str1, str2) {
    let factor = str1.length > str2.length ? str2 : str1;
    while (factor.length) {
        if (
            str1.split(factor).every(e => e === '') &&
            str2.split(factor).every(e => e === '')
        ) {
            return factor;
        }
        factor = factor.slice(0, -1);
    }
    return ''
};

解析版

javascript 复制代码
  var gcdOfStrings = function (str1, str2) {
      let factor = str1.length > str2.length ? str2 : str1 //使用factor先存储str1和str2中的较短者
      // console.log(factor, 'factor')
      while (factor.length) {
        console.log(str1.split(factor), " str1.split(factor)")
        console.log(str2.split(factor), " str2.split(factor)")
        // 判断如果str1 和str2 都能被factor所分隔则这时的factor就是正确答案
        if (
          str1.split(factor).every(e => e === '') &&
          str2.split(factor).every(e => e === '') //split是将字符串根据传入的内容进行分隔存放到一个数组中 
          // "abc".split('b')=>['a','c']   "abbbc".split('b')=> ['a', '', '', 'c']
          // every是遍历数组中的每个元素如果都满足传入的函数的要求则返回true 否则false
        ) {
          return factor
        }

        factor = factor.slice(0, -1)//截取factor 每次删除factor字符串中的最后一个元素
        console.log(factor, "factor")
      }
      return '' //如果循环结束了还没有返回,则没有找到符合条件的factor 返回空字符串
    }
    console.log(gcdOfStrings("ABABAB", "ABAB"))
    console.log("abbbc".split('b'));

运行结果

方法三:暴力仿求最大公因子的辗转相除法

源码版

javascript 复制代码
var gcdOfStrings = function (str1, str2) {
    if (str1 + str2 !== str2 + str1) return ''
    return strGcb(str1, str2)

}
function strGcb(a, b) {
    return (a.split(b).every(e => e === '')) ? b : strGcb(b, a.split(b).filter(e => { if (e !== '') { return e } }).join())
}

解析版

javascript 复制代码
 var gcdOfStrings = function (str1, str2) {
      if (str1 + str2 !== str2 + str1) return '' //首先判断str1 str2是否有最大公因数 
      return strGcb(str1, str2)

    }
    function strGcb (a, b) {
      return (a.split(b).every(e => e === '')) ? b : strGcb(b, a.split(b).filter(e => { if (e !== '') { return e } }).join())
      // a % b === 0 ? b : isgy(b, a % b)  上一行代码是比着这个写出来的

      // a.split(b).every(e => e === ''))  这个等价于 a%b===0 
      // split是将字符串根据传入的内容进行分隔存放到一个数组中 
      // "abc".split('b')=>['a','c']   "abbbc".split('b')=> ['a', '', '', 'c']
      // every是遍历数组中的每个元素如果都满足传入的函数的要求则返回true 否则false

      // a.split(b).filter(e => { if (e !== '') { return e } }).join() 等价于 a % b
      // filter() 遍历数组 得到满足条件的返回值 返回一个新数组 
      // join() 将数组的每一项 用传入的值作为分隔符 拼接成一个字符串
    }

运行结果

相关推荐
小小爱大王35 分钟前
AI 编码效率提升 10 倍的秘密:Prompt 工程 + 工具链集成实战
java·javascript·人工智能
半生过往35 分钟前
2025 前端动效实战指南:Vue Bits & React Bits 深度拆解(功能 / 复用 / 高频问题处理)
前端·vue.js·react.js
程序员包打听38 分钟前
Vitest 4.0 重磅发布:Browser Mode 正式稳定,前端测试进入新纪元
前端
BumBle39 分钟前
UniApp 多页面编译优化:编译时间从10分钟到1分钟
前端
星链引擎43 分钟前
大语言模型的技术突破与稳定 API 生态的构建
前端
还是大剑师兰特43 分钟前
TypeScript 面试题及详细答案 100题 (71-80)-- 模块与命名空间
前端·javascript·typescript
BumBle43 分钟前
使用 SortableJS 实现vue3 + Element Plus 表格拖拽排序
前端·vue.js·element
玉宇夕落43 分钟前
HTML5 音乐敲击乐静态界面
前端
海在掘金6112744 分钟前
告别"拼写错误":TS如何让你的代码"字字精准"
前端
用户479492835691544 分钟前
什么是XSS攻击,怎么预防,一篇文章带你搞清楚
前端·javascript·安全