Metodi Substringa () e StringBuilder delete () di Java

2

Ho notato che alcuni metodi come la sottostringa String (int beginIndex, int endIndex) e l'eliminazione di StringBuilder (int beginIndex, int endIndex), usano il secondo parametro per indicare che la sottostringa o l'eliminazione dovrebbero andare a endIndex-1 e non endIndex. C'è una ragione per questo? Non sembra, almeno per me, avere un senso logico per questi metodi per indicare che il metodo si arresta prima del parametro anziché del parametro, diversamente da altri metodi, in altre classi. Alcuni snippet di esempio potrebbero essere:

Esempio 1:

4: StringBuilder sb = new StringBuilder("abcdef");
5: sb.delete(2, 4);
6: System.out.println(sb);
//This would print abef instead of abf

Esempio 2:

4: String str = "abcdef";
5: String newStr = str.substring(2, 4);
6: System.out.println(newStr);
//This would print cd instead of cde

Questo sembra strano per chiunque altro considerando come funzionano altri metodi con i parametri dell'indice? C'è una ragione per questo? Se è così, per favore, spiegamelo.

Modifica per differenziare e chiarire una domanda unica: Questa domanda è diversa dalla discussione sulla sola sottostringa () poiché riguarda tutti i metodi che usano le indicizzazioni per indicare che il metodo dovrebbe fermarsi prima dell'endIndex fornito (esclusione invece dell'inclusione).

    
posta Steven Mcdonald 14.09.2018 - 01:27
fonte

3 risposte

3

Un motivo pratico è che semplifica le cose in alcune situazioni comuni:

  • Se vuoi che l'operazione includa tutto fino alla fine della stringa, puoi utilizzare direttamente la lunghezza come endIndex
  • Se hai "caratteri di separazione", come il punto tra il nome base e il suffisso tipo file, di solito non vuoi includerli, quindi puoi usare l'indice del carattere di separazione come endIndex , ad es. %codice%
risposta data 14.09.2018 - 09:54
fonte
1

Sono d'accordo con la risposta di Micheal Borgwardt ma c'è un'opportunità di elaborazione. L'approccio che vedi qui non è solo utile, ma anche coerente con la maggior parte delle API che troverai in Java e in molte altre lingue. L'associazione con l'indicizzazione basata su 0 è più chiara se si pensa al for-loop standard vecchio stile: for (int i = 0; i < end; i++) . In questi giorni tendiamo a favorire per ogni stile costrutti, ma questo è il modo in cui viene scritto un sacco di codice. Nota la condizione while, è basata su ed esclusivo termina con < invece di <= . Quando stai scrivendo molti loop come questo, è utile usare ogni volta un costrutto simile.

Ma per capire davvero l'immagine più grande su questo, penso che aiuti a guardare un diverso tipo di problema: intervalli di tempo. Immaginiamo che voglio dire se è successo qualcosa oggi, al mattino. Se strutturo questo come un fine inclusivo, ho quindi un problema di capire quale potrebbe essere l'ultima volta. Ciò significa che ho bisogno di conoscere la più piccola risoluzione dell'orologio. Sono secondi, millisecondi, microsecondi, nanosecondi? Diciamo che penso che i secondi siano abbastanza buoni. Quindi dico "meno o uguale a 11:59". Funziona se è successo alle 11:59 e 30 secondi? Bene, controllerò se "il minuto del giorno è stato inferiore o uguale a 11:59". Oppure potrei dire "meno di mezzogiorno" che è molto più elegante e tende ad essere più robusto.

O considera i periodi di date. Come faccio a sapere se due periodi di data sono adiacenti, cioè che non vi è alcuna differenza intermedia? Se ho usato un fine esclusivo, è banale. Ho appena controllato che la fine (esclusiva) del primo periodo sia uguale o successiva all'inizio (compreso) del secondo. Se uso un fine inclusivo, ora devo uscire da un calendario e capire se il giorno dopo il 30 settembre è il 1 ° ottobre. E il 1 ° marzo segue il 28 febbraio? Che anno è? Dividi questo per 4 a meno che non stiamo parlando dell'ultimo anno del secolo, ma non dimenticare che l'anno 2000 è l'eccezione all'eccezione. Esistono strategie per risolvere questo tipo di cose, ma il più semplice è convertire l'end inclusivo in esclusivo.

    
risposta data 14.09.2018 - 23:22
fonte
0

Il libro SCJP raffigura quanto segue:

"The start index of the substring to be removed is defined by the first argument(which is zero-based), and the ending index of the substring to be removed is defined by the second argument (but it is one-based)!".

StringBuilder sb = new StringBuilder("0123456789")
System.out.println(sb.delete(4,6)) 

L'esempio precedente emette 01236789 [0123XX6789] iniziando la cancellazione dall'indice quattro (4) ed essendo sei (6) l'indice stop (non incluso). In C # ad esempio il metodo Rimuovi di StringBuilder utilizza l'indice iniziale e il numero di caratteri da eliminare Rimuovi (int startIndex, int length) come argomenti della funzione. Quindi l'indice di cancellazione dell'arresto è la chiave per comprendere il metodo di cancellazione della classe Java StringBuilder.

    
risposta data 14.09.2018 - 05:45
fonte

Leggi altre domande sui tag