1.15 String Manipulation
Create strings, concatenate them, and use length(), substring(), indexOf(), equals(), and compareTo(), remembering that String methods never change the original.
1. Reference Guide
| Term | Definition / Example | College Board Requirement |
|---|---|---|
| String literal | Text in double quotes, which creates a String object: String s = "hello"; |
Unit 1, Topic 1.15, p. 48 |
| String constructor | Another way to create one: String s = new String("hello"); |
Unit 1, Topic 1.15, p. 48 |
| Immutable | A String object never changes; methods return a new String instead |
Unit 1, Topic 1.15, p. 48 |
| Concatenation | + or += joins Strings, or a String and a primitive, into a new String: "Score: " + 10 |
Unit 1, Topic 1.15, p. 48 |
| Index | A character’s position, starting at 0: in "code", c is at 0 and e is at 3 |
Unit 1, Topic 1.15, p. 49 |
StringIndexOutOfBoundsException |
Run-time error from an index below 0 or past the end: "code".substring(2, 5) |
Unit 1, Topic 1.15, p. 49 |
- The last index of a String is
length() - 1 - Compare Strings with
equals, not==.==checks whether two references point to the same object
String Methods (AP Java Quick Reference)
| Method | Returns | Example with s = "computer" |
|---|---|---|
int length() |
The number of characters | s.length() is 8 |
String substring(int from, int to) |
Characters from from up to, not including, to |
s.substring(0, 3) is "com" |
String substring(int from) |
Characters from from to the end |
s.substring(3) is "puter" |
int indexOf(String str) |
Where str first starts, or -1 if it is not there |
s.indexOf("put") is 3 |
boolean equals(Object other) |
true if the characters are the same |
s.equals("computer") is true |
int compareTo(String other) |
Negative, 0, or positive for before, same, or after in dictionary order |
"apple".compareTo("banana") is negative |
Reading substring
Call on "computer" |
Indexes used | Result |
|---|---|---|
substring(2, 5) |
2, 3, 4 | "mpu" |
substring(0, 1) |
0 | "c" (the first letter) |
substring(7) |
7 | "r" (the last letter) |
substring(8) |
none | "" (an empty String) |
substring(2, 9) |
past the end | StringIndexOutOfBoundsException |
Spotting Immutability
- A method is called but its result is not stored → nothing changed; the original String is the same
- You want the change to stick → assign the result:
s = s.substring(1); +joins a String and a number → the result is a new String:"Total: " + 5 + 3is"Total: 53"
College Board Requirements
AP CSA Unit 1, Topic 1.15 String Manipulation. Quoted from the course and exam description (College Board, 2025, pp. 48-49):
- “A String object represents a sequence of characters and can be created by using a string literal or by calling the String class constructor.”
- “A String object is immutable, meaning once a String object is created, its attributes cannot be changed. Methods called on a String object do not change the content of the String object.”
The Java language specification states the same rule: String objects have a constant, unchanging value (Gosling et al., 2023, section 4.3.3).
Reference: College Board, AP Computer Science A Course and Exam Description (2025), Unit 1, Topic 1.15, pp. 48–49.
2. Real-Life Application
Gene Names That Turned Into Dates
Scientists name human genes with short strings like SEPT2 and MARCH1. When researchers opened their data in a spreadsheet, the program read those strings as dates and changed them to “2-Sep” and “1-Mar”, quietly corrupting gene lists in published research. In 2020 the official gene naming committee renamed them SEPTIN2 and MARCHF1 so the text would stay text. Everyone guess: why was it easier to rename the genes than to fix every spreadsheet?
| Real Case | What Happened | Java Idea in This Lesson |
|---|---|---|
| Gene names (renamed in 2020) | Text that looked like a date was treated as a date | A String is just characters; code decides what they mean |
| People named Null | Some systems reject or lose the surname “Null” because they treat the text as “no value” | "Null".equals(name) is a String comparison; null is no object at all |
| Email addresses | A sign-up form splits ada@school.org at the @ |
indexOf("@") and substring |
| Usernames | ada plus lovelace becomes alovelace |
first.substring(0, 1) + last |
The takeaway: treat text as text. Find positions with indexOf, cut with substring, compare with equals, and remember that each method gives back a new String.
3. Tech Talk
Learning Objective: Create and concatenate Strings, and use length, substring, indexOf, equals, and compareTo to work with them.
Success Criteria: You can predict the result of any String method in the Reference Guide, find and cut out part of a String, and explain why calling a method does not change the original String.
Indexes start at 0, and the second number in substring is where it stops, not counted:
String s = "hello world";
System.out.println(s.length()); // 11
System.out.println(s.indexOf("world")); // 6
System.out.println(s.substring(0, 5)); // hello
System.out.println(s.substring(6)); // world
A String never changes. Store the result if you want to keep it:
s.substring(6); // the result is thrown away
System.out.println(s); // hello world
s = s.substring(6); // s now refers to a new String
System.out.println(s); // world
Code Examples
A. Creating and joining Strings. The StringBasics class shows literals, the constructor, concatenation, and immutability
s1 + s2 builds a new String, so s1 is printed again afterward to show it did not change:
String s3 = s1 + s2; // a new String
s1 += "!"; // s1 now refers to another new String
Terminology:
Immutable: no method changes a String’s characters. += does not change the old String either; it points the variable at a new one.
Code Runner Challenge
Predict every line, run it, then change s2 and predict again
View IPYNB Source
// CODE_RUNNER: Predict every line, run it, then change s2 and predict again
public class StringBasics {
public static void main(String[] args) {
String s1 = "hello"; // a literal
String s2 = new String("world"); // the constructor
System.out.println(s1);
System.out.println(s2);
String s3 = s1 + " " + s2; // concatenation makes a new String
System.out.println(s3);
System.out.println(s1); // s1 did not change
String score = "Score: " + 7 + 3; // left to right: joins 7, then 3
String total = "Total: " + (7 + 3); // parentheses add first
System.out.println(score);
System.out.println(total);
s1 += "!"; // s1 now refers to a new String
System.out.println(s1);
System.out.println("She said \"hi\""); // \" puts a quote inside a String
}
}
StringBasics.main(null);
B. String methods. The StringMethods class calls every method from the Reference Guide
s2 is "hihihellothere". Before you run, find where "hello" starts by counting from 0:
h i h i h e l l o t h e r e
0 1 2 3 4 5 6 7 8 9 ...
Terminology:
compareTo compares in dictionary order, letter by letter. A negative result means the first String comes first.
Code Runner Challenge
Predict each result, run it, then search s2 for a word that is not there
View IPYNB Source
// CODE_RUNNER: Predict each result, run it, then search s2 for a word that is not there
public class StringMethods {
public static void main(String[] args) {
String s1 = "hello";
String s2 = "hihihellothere";
System.out.println(s2.length()); // 14
System.out.println(s2.indexOf(s1)); // 4: where hello starts
System.out.println(s2.indexOf("bye")); // -1: not found
String s3 = s2.substring(4, 9); // indexes 4 to 8
System.out.println(s3);
System.out.println(s2.substring(9)); // from index 9 to the end
System.out.println(s3.equals(s1)); // same characters
System.out.println(s2.equals(s1));
System.out.println(s1.compareTo(s2)); // e comes before i: negative
System.out.println(s2.compareTo(s1)); // positive
System.out.println(s3.compareTo(s1)); // 0: equal
System.out.println(s2); // unchanged by every call above
}
}
StringMethods.main(null);
Hacks & Practice Tasks
Lesson: CSA 1.15 String Manipulation
MCQ 1.15: <paste the copied result line, such as 3/4 | answers: B,C,A,D>
Popcorn: email split with indexOf and substring, original unchanged (yes/no); predicted index of @ = <p>; actual = <a>
Homework Hack 1: prediction = <what shortTitle printed before the fix>, all three checks print true (yes/no)
Homework Hack 2: all three username checks print true (yes/no)
Homework Hack 3: all four swapHalves and firstAlphabetically checks print true (yes/no)
Submission Safety Rules (Read First)
- One class per cell, ending with
ClassName.main(null);. - Label the homework hacks 1 through 3.
- Write your predictions before you run.
- Store the result of a String method if you want to keep it; never claim a method changed the original.
- Run each Java cell and leave the output showing.
- Include your MCQ score.
- Use
##headings or smaller.
Popcorn Hack (In-Class)
3-minute challenge: split an email address at the @.
- Find the position of
"@"withindexOf - Use
substringto get everything before it (the username) and everything after it (the domain) - Do not type
"ada.lovelace"or"school.org"yourself: compute them fromemail - Predict the index of
@in the Popcorn checker under the runner before you run. When every check passes, copy its line into your submission notes
The last line prints email again to show it did not change.
Code Runner Challenge
Find the @ with indexOf, cut the email with substring, predict the index, then run it
View IPYNB Source
// CODE_RUNNER: Find the @ with indexOf, cut the email with substring, predict the index, then run it
// Practice #1 - Try it yourself first!
public class EmailSplitter {
public static void main(String[] args) {
String email = "ada.lovelace@school.org";
int at = 0; // TODO: where "@" is, using indexOf
String username = ""; // TODO: everything before the @, using substring
String domain = ""; // TODO: everything after the @, using substring
System.out.println("Index of @: " + at);
System.out.println("Username: " + username);
System.out.println("Domain: " + domain);
System.out.println("Email: " + email);
}
}
EmailSplitter.main(null);
Before you press Run, predict this output. Count the characters from 0.
4. MCQ Check
4 questions, one at a time. Answer, check, then go to the next one. At the end, copy the score line into your submission notes.
5. Homework Hack
Task: Do all three hacks. Each starter compiles and runs, so you can run the initial version and compare its incorrect output with the expected output. Change only what the TODO asks for, and keep going until every check prints true.
Solution Skeleton:
Hack 1: The Change That Did Not Stick (5 minutes)
Immutability.
Part 1: Predict. Before you change anything, what does the shortTitle line print? Write it in prediction, then run it.
Part 2: Fix the bug. shortTitle should be "Java", but the result of substring is thrown away. Store it in shortTitle. title itself must not change.
Code Runner Challenge
Write your prediction, run it, then store the substring result so all three checks print true.
View IPYNB Source
// CODE_RUNNER: Write your prediction, run it, then store the substring result so all three checks print true.
public class ImmutableHack {
public static void main(String[] args) {
String title = "Java Programming";
String shortTitle = title;
title.substring(0, 4); // TODO: the result is thrown away; store it in shortTitle instead
// Part 1: what does the next line print BEFORE your fix?
String prediction = "TODO: your prediction";
System.out.println("shortTitle: " + shortTitle);
System.out.println(prediction.equals("Java Programming"));
System.out.println(shortTitle.equals("Java"));
System.out.println(title.equals("Java Programming"));
}
}
ImmutableHack.main(null);
Hack 2: Username Generator (5 minutes)
substring and concatenation. A username is the first letter of the first name followed by the whole last name: ada and lovelace become alovelace. Write makeUsername with substring and +. The names are already lowercase.
Code Runner Challenge
Write makeUsername with substring and + so all three checks print true.
View IPYNB Source
// CODE_RUNNER: Write makeUsername with substring and + so all three checks print true.
public class UsernameHack {
// TODO: return the first letter of first, followed by all of last
public static String makeUsername(String first, String last) {
return "";
}
public static void main(String[] args) {
System.out.println("Username: " + makeUsername("ada", "lovelace"));
System.out.println(makeUsername("ada", "lovelace").equals("alovelace"));
System.out.println(makeUsername("grace", "hopper").equals("ghopper"));
System.out.println(makeUsername("alan", "turing").length() == 7);
}
}
UsernameHack.main(null);
Hack 3: Swap and Sort (10 minutes)
Combined.
swapHalves(s)returns the second half followed by the first half. Split ats.length() / 2, so for an odd length the extra character goes in the second half:"hello"becomes"llohe".firstAlphabetically(a, b)returns whichever String comes first in dictionary order. UsecompareTo.
Code Runner Challenge
Write swapHalves and firstAlphabetically so all four checks print true.
View IPYNB Source
// CODE_RUNNER: Write swapHalves and firstAlphabetically so all four checks print true.
public class SwapAndSort {
// TODO: split at s.length() / 2 and return the second half + the first half
public static String swapHalves(String s) {
return s;
}
// TODO: use compareTo to return the String that comes first in dictionary order
public static String firstAlphabetically(String a, String b) {
return a;
}
public static void main(String[] args) {
System.out.println(swapHalves("abcdef") + " " + firstAlphabetically("pear", "apple"));
System.out.println(swapHalves("abcdef").equals("defabc"));
System.out.println(swapHalves("hello").equals("llohe"));
System.out.println(firstAlphabetically("pear", "apple").equals("apple"));
System.out.println(firstAlphabetically("cat", "dog").equals("cat"));
}
}
SwapAndSort.main(null);
Grading Plan (1 Point Total)
| Part | Points | What earns the points |
|---|---|---|
| Popcorn | 0.2 | The index is predicted before running, and the username and domain come from indexOf and substring, with the original email unchanged. The Popcorn checker line is in the notes. |
| MCQ | 0.2 | 4 correct. 0.15 for 2 or 3, 0.1 if every question was answered. |
| Homework Hack 1 | 0.15 | The prediction was written before the fix, the substring result is stored, and all three checks print true. |
| Homework Hack 2 | 0.2 | makeUsername uses substring and +, and all three checks print true. |
| Homework Hack 3 | 0.25 | swapHalves splits at length() / 2, firstAlphabetically uses compareTo, and all four checks print true. |
| Total | 1.0 |
Quick Validation Checklist
- Each cell ends with
ClassName.main(null);and shows output. - Popcorn checker line in the notes.
- MCQ score in the notes.
- Every String result you need is stored in a variable.
- Strings compared with
equalsorcompareTo, not==. - Every homework check prints
true.
6. LxD Cycle Process
Empathize: Students write s1.substring(1) and expect s1 itself to change. They treat String methods like ArrayList methods, which really do change the object, and they lose track of indexes because counting starts at 0 and substring stops before its second number.
Define:
- POV: CSA students need to see that a
Stringnever changes, because the AP exam often tests code that wrongly assumes a String method changed the original variable. - Learning Goal: Students will create and concatenate Strings, predict the results of
length,substring,indexOf,equals, andcompareTo, and store results instead of expecting the original to change.
Ideate:
- HMW Question: How might we make immutability visible, something students see fail rather than just hear about?
- HMW Question: How might we make index counting automatic before students reach loops over Strings in Unit 2?
- Activity: Print the original String after each method call, split an email at the
@, then fix a change that did not stick and build usernames.
Prototype:
- A reference guide with the AP String methods and a substring table, runnable creation and methods examples, an email-splitting Popcorn Hack with a checker, an MCQ knowledge check, three scaffolded homework hacks with self-checking output, and a grading rubric.
- The earlier version spent most of its examples on
Dogobjects,Arrays.sort,Math, and wrapper classes, which belong to Topics 1.11 to 1.14. It now stays on Strings, the subject of Topic 1.15. - Excellence means predicting every index and result exactly, and storing each String result that needs to be kept.
Test:
- Ask peers in peer review to complete the practice without additional explanation.
- Observe whether peers count indexes from 0, and whether they expect a method call to change the original String.
- Compare your lesson with another that is posted.
- Use the findings to revise any instruction or rubric criterion that did not guide students clearly.
- On submission, collect evidence from runner output, MCQ results, AI grading and student explanations.
- After teaching, grading and analysis, come back and revise lesson to complete teaching cycle for continuous improvement.
7. References/Citations
Bruford, E. A., Braschi, B., Denny, P., Jones, T. E. M., Seal, R. L., & Tweedie, S. (2020). Guidelines for human gene nomenclature. Nature Genetics, 52(8), 754–758. https://doi.org/10.1038/s41588-020-0669-3
College Board. (2025). AP Computer Science A course and exam description [Effective fall 2025]. https://apcentral.collegeboard.org/media/pdf/ap-computer-science-a-course-and-exam-description-effective-fall-2025.pdf
Gosling, J., Joy, B., Steele, G., Bracha, G., Buckley, A., Smith, D., & Bierman, G. (2023). The Java® language specification (Java SE 21 ed., section 4.3.3, The class String). Oracle. https://docs.oracle.com/javase/specs/jls/se21/html/jls-4.html
Submit Assignment
Need to update a submission later? Open the submissions dashboard.