字符串数组中两个字符的最短距离

[leetcode] https://leetcode.com/problems/shortest-word-distance/

For example,
Assume that words = ["practice", "makes", "perfect", "coding", "makes"].

Given word1 = “coding”word2 = “practice”, return 3.
Given word1 = "makes"word2 = "coding", return 1.

需要注意:

  1. 该数组中得字符串有可能出现多次,比如例子中的makes;

这个问题比较简单,按照下面的步骤可以简单的做出来:

  1. 记录给定两个字符串出现的位置,会得到两个数组;假设为a和b;

  2. 然后计算abs(a[i] - b[j])的最小值即可;

第一步扫描一遍字符串数组即可;第二步,如果简单的用两层循环来做,因为a和b的长度都有可能是n(比如各占一半),那么用O(n * n)的时间;

事实上,有意思的地方就在于,第二步可以在线性时间内解出来;这里有一个隐藏的特性,扫描原数组的时候得到的两个字符的位置数组,是有序的;比如数组 [a, b, a, b, b, a], 那么a的位置数组为[0, 2, 5], b的为[1, 3, 4]; 假设我们比较到了位置2和位置3,我们是没有必要去比较位置2和4的;因为后者的距离肯定大于前者;用下面的图可能更清楚;

213525_AApz_922297.png

213525_a7Ul_922297.png

214222_EpZw_922297.png

214222_vihi_922297.png

所以,可以得到这样的关系,当a < b的时候,增加a的坐标,当a > b的时候,增加b的坐标;这样就可以在o(n)的时间内完成;

public int shortestDistance(String[] words, String word1, String word2) {
    int[] indexes1 = new int[words.length];
    int[] indexes2 = new int[words.length];
    int m = 0, n = 0;
    for (int i = 0; i < words.length; i++) {
        String word = words[i];
        if (word.equals(word1)) {
            indexes1[m++] = i;
        } else if (word.equals(word2)) {
            indexes2[n++] = i;
        }
    }
    int dist = Integer.MAX_VALUE;

    for (int i = 0, j = 0; i < m && j < n; ) {
        int x = indexes1[i];
        int y = indexes2[j];
        dist = Math.min(dist, Math.abs(x - y));
        if (x < y) {
            i++;
        } else {
            j++;
        }
    }

    return dist;
}


转载于:https://my.oschina.net/u/922297/blog/494172

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值