LeetCode 2100. Un buen día para robar un banco

【LetMeFly】2100. Un buen día para robar un banco

Ahora parece que 2100. 适合野炊的日子se ha .

Enlace de pregunta de Leetcode: https://leetcode.cn/problems/find-good-days-to-rob-the-bank/

Tú y un grupo de ladrones vais a robar un banco. Se le proporciona una serie de números enteros cuyo índice  comienza  en 0security  , donde  security[i] es i el número de guardias de servicio ese día. Los días 0 están contados desde el principio. También te da un número entero  time .

Si i el día cumple todas las condiciones siguientes, lo llamamos un día adecuado para robar un banco:

  • i Hay al menos un día antes y después del primer día time .
  • i El número de guardias en días consecutivos antes del primer día time no aumenta.
  •  El número de guardias no disminuye en días i consecutivos después del primer día.time

Más formalmente, el día ies un día adecuado para robar un banco si y sólo si: security[i - time] >= security[i - time + 1] >= ... >= security[i] <= ... <= security[i + time - 1] <= security[i + time].

Devuelva una matriz que contenga todos los días adecuados para el robo a un banco (el subíndice comienza en 0  ). Los días devueltos pueden estar en  cualquier orden.

 

Ejemplo 1:

Entrada: seguridad = [5,3,3,3,5,6,2], tiempo = 2
 Salida: [2,3]
 Explicación: 
El día 2, tenemos seguridad[0] >= seguridad[1] >= seguridad[2] <= seguridad[3] <= seguridad[4] . 
El día 3, tenemos seguridad[1] >= seguridad[2] >= seguridad[3] <= seguridad[4] <= seguridad[5] . 
Ningún otro día cumple con este criterio, por lo que los días 2 y 3 son buenos días para robos a bancos.

Ejemplo 2:

Entrada: seguridad = [1,1,1,1,1], tiempo = 0
 Salida: [0,1,2,3,4]
 Explicación: 
Debido a que el tiempo es igual a 0, cada día es un día adecuado para robar un banco Así que regresa todos los días.

Ejemplo 3:

Entrada: seguridad = [1,2,3,4,5,6], tiempo = 2
 Salida: []
 Explicación: 
No hay un número no creciente de guardias en los primeros 2 días de cualquier día. 
Por lo tanto, no hay días adecuados para el robo de un banco y se devuelve una matriz vacía.

 

pista:

  • 1 <= security.length <= 105
  • 0 <= security[i], time <= 105

Ideas

Método 1: discusión sobre clasificación

<complejidad de tiempo pequeño O ( n ) O (n)O ( n ) , complejidad espacial O (1), dificultad ※※** </smtps://leetcode-cn.com/problems/find-good-days-to-rob-the-bank/solution/letmefly-fen -lei-tao-lun-on-o1-by-letmef-1jgw/](https://img-blog.csdnimg.cn/img_convert/ca4a6ec46181f3756420620dbe776075.jpeg)

tiempo = 0 tiempo = 0tiempo _ _=En el caso de 0, se debe prestar especial atención a la inserción de enlaces e imágenes.

Por lo tanto usamos dos variables lian X u X ia D ays lianXuXiaDaysl ian X u X ia D a ys (que representa días no crecientes) ymight A s Up 4 B egin mightAsUp4Beginco u l d A s Up 4 Be g in (El día a partir de ahora en el que puede comenzar la no disminución)

Es decir, en lianXuXiaDays consecutivosl ian X u X ia Días después de días no crecientes, si lian X ul ian X u X ia D a ysti im e , entonces siempre y cuandotiempocontinuohoyEl tiempo no disminuye día a día, hoy es el "día del robo" .

Entonces estamos en lian X u X ia D ays ≥ tiempo lianXuXiaDays\geq tiempol ian X u X ia D a yscuando el tiempo , puedes cambiar might A s Up 4 B egin mightAsUp4Beginco u l d A s Up 4 Comenzar Márquelo como hoy . _

Si el tiempo despuésLos días de tiempo y superiores no están disminuyendo, entonces el registropodría A s Up 4 Begin mightAsUp4Begin en este momentoco u l d A s Up 4 Be g in es un "día de robo " .

Por lo tanto, en el recorrido hacia atrás, si todavía está en el estado no decreciente, se puede juzgar si podría existir A s Up 4 B egin mightAsUp4Beginco u l d A s U p 4 B e g in , si hay (≠ − 1 \neq -1=1 ) Simplemente juzgue la distancia de hoy.might A s Up 4 B egin mightAsUp4Beginco u l d A s U p 4 B e g en si≥ tiempo \geq tiempot im e días si≥ tiempo \geq tiempot im e, El empleopodría A s Up 4 B egin mightAsUp4Beginco u l d A s Up 4 Be g en el tiempocontinuo _tiempo los días no son decrecientes, por lo quepodría A s Up 4 Begin podría AsUp4Beginco u l d A s Up 4 Be g in es un día de robo .

Para una descripción más detallada, consulte los comentarios.

código de CA

C++
class Solution {
    
    
public:
    vector<int> goodDaysToRobBank(vector<int>& security, int time) {
    
    
        if (!time) {
    
      // time = 0,每天都是“打劫日”
            vector<int> ans(security.size());  // 答案共有security.size()天
            for (int i = 0; i < security.size(); i++) {
    
    
                ans[i] = i;  // 第i个答案是第i天
            }
            return ans;
        }
        vector<int> ans;
        int lianXuXiaDays = 0;  // 连续↓或→的天数
        int couldAsUp4Begin = -1;  // 最早可以认为是开始连续上升的那一天 | 如果couldAsUp4Begin=a≠-1,说明第a天之前至少有time天的非递增
        for (int i = 1; i < security.size(); i++) {
    
      // 从第二天开始遍历
            if (security[i] < security[i - 1]) {
    
      // ↓
                lianXuXiaDays++;  // 连续非递增天数++
                if (lianXuXiaDays >= time) {
    
      // 如果连续非递增天数≥time,那么今天之前就有≥time的非递减
                    couldAsUp4Begin = i;  // 从今天开始可以非递减了
                }
                else {
    
      // 还没有连续非递增time天
                    couldAsUp4Begin = -1;
                }
            }
            else if (security[i] == security[i - 1]) {
    
      // 今天和昨天相等,也就是说既符合非递增又符合非递减
                lianXuXiaDays++;  // 符合非递增,连续非递增天数++
                if (couldAsUp4Begin != -1) {
    
      // 前面有≥time的非递减,并且从那天起没有递增的一天 | Lable1
                    if (i - couldAsUp4Begin >= time) {
    
      // 如果今天距离那天≥time,那天就是抢劫日
                        ans.push_back(couldAsUp4Begin);  // 先把抢劫日添加到答案中去
                        if (security[couldAsUp4Begin + 1] <= security[couldAsUp4Begin]) {
    
      // 如果抢劫日的下一天仍然是非递增,那么下一天之前肯定有至少time天的非递增
                            couldAsUp4Begin++;  // 下一天也可以作为开始非递减的一天
                        }
                        else {
    
      // 否则
                            couldAsUp4Begin = -1;  // 下一天>这个抢劫日,说明下一天必不满足“前面有至少time天的非递增”
                        }
                    }
                }
                else {
    
      // couldAsUp4Begin = -1
                    if (lianXuXiaDays >= time) {
    
      // 连续非递增天数≥time
                        couldAsUp4Begin = i;  // 从今天起可以开始非递减了
                    }
                }
            }
            else {
    
      // 今 > 昨
                lianXuXiaDays = 0;  // 连续非递减天数中断
                if (couldAsUp4Begin != -1) {
    
      // 这个同理于上面的“Lable1”处
                    if (i - couldAsUp4Begin >= time) {
    
    
                        ans.push_back(couldAsUp4Begin);
                        if (security[couldAsUp4Begin + 1] <= securmai ty[coul AsUp4Begin])   {
    
                         couldA Up4B gectin++;
                           }
 已完成          else {
    
    
                  }
 couldA     }
        }
Up4Begin = -1;
                       }
                    }
                }
            }
        return ans;  // 返回答案即可
    }
};

Método dos

Complejidad del tiempo O ( n ) O (n)O ( n ) , complejidad espacial O (n), dificultad ※

Este método es más fácil de implementar que el método anterior, pero la complejidad del espacio es mayor que el método anterior.

Podemos usar O ( n ) O(n)La complejidad temporal de O ( n ) es encontrar el "número de días consecutivos no crecientes antes" y "el número de días consecutivos no decrecientes después" para cada día.

x i a [ i ] xia[i] x ia [ i ] pantalla nºiiHay días que no aumentan antes del día i ,shang [ i ] shang [i]s han g [ i ] pantalla nºii¿Cuántos días antes del día i son no decrecientes?

Método específico: atravesar la matriz de adelante hacia atrás, si 今天≤昨天 , entonces xia[i] = xia[i - 1] + 1 ; en caso contrario xia[i] = 0 ,. Valor inicial xia[0] = 0 Recorre la matriz de atrás hacia adelante, si 今天≤昨天 , entonces shang[i] = shang[i + 1] + 1 ; en caso contrario shang[i] = 0 ,. valor inicial shang[security.size() - 1] = 0

Luego recorremos cada día, si un día satisface xia [ i ] ≥ time xia[i]\geq timexia [ yo ] _t im eshang [ i ] ≥ tiempo shang[i] \geq tiemposhang [ yo ] _ _Tiempo , este día es el día del robo.

código de CA

C++
class Solution {
    
    
public:
    vector<int> goodDaysToRobBank(vector<int>& security, int time) {
    
    
        vector<int> xia(security.size());
        vector<int> shang(security.size());
        xia[0] = 0, shang[shang.size() - 1] = 0;
        for (int i = 1; i < security.size(); i++) {
    
    
            xia[i] = security[i] > security[i - 1] ? 0 : xia[i - 1] + 1;
        }
        for (int i = security.size() - 2; i >= 0; i--) {
    
    
            shang[i] = security[i] > security[i + 1] ? 0 : shang[i + 1] + 1;
        }
        vector<int> ans;
        for (int i = 0; i < security.size(); i++) {
    
    
            if (xia[i] >= time && shang[i] >= time)
                ans.push_back(i);
        }
        return ans;
    }
};

El artículo se publica simultáneamente en CSDN. No es fácil ser original. Adjunte el enlace al artículo original después de la reimpresión con el consentimiento del autor ~
Tisfy: https://letmefly.blog.csdn.net/article/details/133324938

Supongo que te gusta

Origin blog.csdn.net/Tisfy/article/details/133324938
Recomendado
Clasificación