StringBuffer์ StringBulider
by JiwonDev2021.07.27 - [๊ธฐ๋ณธ ์ง์/CS ๊ธฐ๋ณธ์ง์] - ์๋ฐ์ String๊ณผ Constant Pool
์๋ฐ์์ ๋ฌธ์์ด์ ๋ค๋ฃจ๋ ๋ฐฉ๋ฒ์ String, StringBuffer, StringBuilder๊ฐ ์๋ค.
์ฌ์ค ์ฐ์ฐ์ด ๋ง์ง ์์ ๋์๋ 3๊ฐ์ค ์๋ฌด๊ฑฐ๋ ์ฌ์ฉํด๋ ํฐ ์ฐจ์ด๋ ์์ง๋ง, ์ฐ์ฐ ํ์๊ฐ ๋ง์์ง๊ฑฐ๋ ๋ฉํฐ์ฐ๋ ๋, Race Condition๋ฑ์ ์ํฉ์ด ๋ฐ์ํ๋ค๋ฉด ๊ฐ ๋ฌธ์์ด ํด๋์ค์ ์ฉ๋๋ฅผ ์ ์๊ณ ์ฌ์ฉํด์ผ ํ๋ค.
# String
S๊ฐ์ฅ ํฐ ํน์ง์ String์ ์์. ์ฆ ๋ถ๋ณ(immutable)ํ๋ค๋ ๊ฒ์ด๋ค.
String str = "hello"; // String str = new String("hello");
str = str + " world"; // [ hello world ]
์ฝ๋์์์๋ ๋ง์น ๋ฌธ์์ด์ 'ํธ์ง' ํ ๊ฒ์ฒ๋ผ ๋ณด์ด๊ฒ ์ง๋ง, JVM ๋ด๋ถ์์๋ ์๋์ ๊ฐ์ ๋์์ด ์ผ์ด๋๋ค. ์ฆ ๋ฌธ์์ด์ ์กฐ์(์ถ๊ฐ, ์์ , ์ญ์ )ํ๋ค๋ฉด Heap ๋ฉ๋ชจ๋ฆฌ๋ฅผ ๋ญ๋นํ๊ณ GC์ ์์ ์ ์ถ๊ฐ์์ผ ์ฑ์ ์ฑ๋ฅ์ ํ๋ฝ์ํจ๋ค.
* ์ฅ? new๋ก ์์ฑํ๊ฒ ์๋ ๋ฌธ์์ด์ Heap์ด ์๋๋ผ ์ ์ ์์๋ก ๊ด๋ฆฌ๋๋๊ฑฐ ์๋์์?
Java8๋ถํฐ๋ ์์ ํ๋ Heap๋ฉ๋ชจ๋ฆฌ์ ์์นํ๊ฒ ๋๋ค. ์ฆ GC์ ๋์์ด๋ค. ๋ํ ๋ฉ๋ชจ๋ฆฌ์ ์ธ ์ธก๋ฉด๋ฟ ์๋๋ผ ๋ฌธ์์ด ์กฐ์ ์ฑ๋ฅ์ด ๊ตฌ๋ฆฌ๋ค๋ ๋จ์ ๋ ์๋ค๋๊ฑธ ์์ง๋ง์.
# StringBuffer์ StringBuilder
String๊ณผ ๋ค๋ฅด๊ฒ ๊ฐ๋ณ์ฑ(mutable)์ ๊ฐ์ ธ ๋ฌธ์์ด ์กฐ์(์ถ๊ฐ, ์์ , ์ญ์ ) ์ฑ๋ฅ์ด ์ข๋ค. ๊ทธ๋ ๋ค๋ฉด ๊ธฐ์กด์ String์ ์ ๋ถ StringBuffer๋ก ๋ฐ๊พธ๋ฉด ๋๋๊ฑฐ ์๋๊น?
String์ ๋จ์ํ ์์๋ฌธ์์ด๋ง ๊ฐ์ง๊ณ ์์ผ๋ฉด ๋์ง๋ง, StringBuffer, Builder๋ ๋ฒํผ์ ํฌ๊ธฐ๋ฅผ ์กฐ์ํ๊ณ ๋ค์ํ ์ถ๊ฐ ๋ฉ์๋๋ฅผ ์ ๊ณตํ๋ ๋งํผ ๋ด๋ถ ๋์์ด ๋ ๋ณต์กํ๋ค. ์ฆ ์กฐ์ํ ํ์๊ฐ ์๋ ๋ชจ๋ String์ StringBuffer์ผ๋ก ์ฒ๋ฆฌํ๋๊ฑด ์ฑ๋ฅ์ ์ข์ง์์ ๋ฐฉ๋ฒ์ด๋ค.
StringBuffer sb= new StringBuffer("hello");
sb.append(" world");
@ String์ ์ค๋ ๋ ์์ ์ฑ
String์ ๊ฒฝ์ฐ ๊ฐ์ด ๋ถ๋ณํ๊ธฐ์ ์ฌ๋ฌ ์ฐ๋ ๋๊ฐ ๋์์ ์ ๊ทผ, ์ฌ์ฉํ๋๋ผ๋ ๋์ผํ ๊ฒฐ๊ณผ๊ฐ์ ๋ฐํํ๋ค. ํ์ง๋ง StringBuilder์ str.append() ์ฐ์ฐ์ฒ๋ผ ๋ฌธ์์ด์ด ๋ถ๋ณํ์ง ์๊ณ ๊ธธ์ด๊ฐ ๋ณํ ์ ์๋ ๊ฒฝ์ฐ ์ฌ๋ฌ ์ฐ๋ ๋๊ฐ ์ ๊ทผ ํ์ ๋ ์ด๋ค ๋ฌธ์ ์ ์ด ์์๊น?
์คํธ๋ง ๊ฐ์ ์ฌ์ฉํจ์ ์์ด DB์ ํธ๋์ญ์ ์ฒ๋ฆฌ, ์ฆ ๋๊ธฐํ๋ฅผ ํด์ฃผ์ง ์์ผ๋ฉด ์ ๋ง ๋ค์ํ ๋ฌธ์ ๊ฐ ์๊ธธ ์ ์๋ค. ์๋ฅผ ๋ค์ด [์ฐ๋ ๋1]์ด ๋ฌธ์์ด์ ํธ์งํ๊ณ ์๋ ๋์ค์ [์ฐ๋ ๋2]๊ฐ ์ ๊ทผํ๋ค๋ฉด ํธ์ง๋๋ค๊ฐ ๋ง์ ์ด์ํ ๊ฐ์ ๊ฐ์ ธ๊ฐ๊ฑฐ๋, ํน์ ๋์์ ์ ๊ทผํ [์ฐ๋ ๋2]๊ฐ [์ฐ๋ ๋1]์ ์์ ๊ฒฐ๊ณผ๋ฅผ ๋ฌด์ํ๊ณ ๋ฎ์ด์์ฐ๋ ๋ฑ ์ ๋ง ์ฌ๊ฐํ ์ค๋ฅ๋ฅผ ๋ผ ์ ์๋ค.
@ StringBuffer vs StringBuilder, ์ฐจ์ด์
๊ฐ์ฅ ํฐ ์ฐจ์ด์ ์ ๋๊ธฐํ์ ์ ๋ฌด์ด๋ค. ์ด๋ฆ์์ ์ ์ ์๋ฏ์ด StringBuffer๋ ๋ฉํฐ์ฐ๋ ๋ ํ๊ฒฝ์์ ์ฌ์ฉ์ ์ํด ๋ง๋ค์๋ค.
- String: ๋ฌธ์์ด ์ฐ์ฐ์ด ์ ๊ณ ๋ฉํฐ์ฐ๋ ๋ ํ๊ฒฝ์ผ ๊ฒฝ์ฐ (๊ฐ์ด ๋ณํ์ง ์์ ์์ ํ๋ค.)
- StringBuffer: ๋ฌธ์์ด ์ฐ์ฐ์ด ๋ง๊ณ ๋ฉํฐ์ฐ๋ ๋ ํ๊ฒฝ์ผ ๊ฒฝ์ฐ (๊ฐ์ด ๋ณํ์ง๋ง, thread-safe๋ฅผ ๋ณด์ฅํ๋ค.)
- StringBuilder: ๋ฌธ์์ด ์ฐ์ฐ์ด ๋ง๊ณ ๋จ์ผ์ฐ๋ ๋์ด๊ฑฐ๋ ๋๊ธฐํ๋ฅผ ๊ณ ๋ คํ์ง ์์๋ ๋๋ ๊ฒฝ์ฐ
StringBuffer์ ๊ฒฝ์ฐ ์๋ฐ์ synchronized ํค์๋๋ฅผ ์ด์ฉํด ๋ฉํฐ์ค๋ ๋์ ๋๊ธฐํ, thread-safe๋ฅผ ๋ณด์ฅํ๋ค.
// StringBuilder.append()
@Override
public StringBuilder append(String str) {
super.append(str);
return this;
}
// StringBuffer.append()
@Override
public synchronized StringBuffer append(String str) {
toStringCache = null;
super.append(str);
return this;
}
๋ค๋ง ๋๊ธฐํ๋ฅผ ๋ณด์ฅํ๋ ์์ ์ ์ฑ๋ฅ์ ํฌ๊ฒ ํ๋ฝ์ํจ๋ค. ์ฆ StringBuffer์ ์ฌ์ฉ์ ๋ฉํฐ์ฐ๋ ๋, ๋จ์ผ์ฐ๋ ๋ ์ฌ๋ถ์ ์๊ด์์ด '๋๊ธฐํ' ๊ธฐ๋ฅ์ ์ถ๊ฐ ๋๋ฌธ์ ์ฑ๋ฅ์ด ํ๋ฝ๋๋ค. ๊ทธ๋์ ๋๊ธฐํ๊ฐ ํ์์๋ ๋จ์ผ ์ฐ๋ ๋์์ ์ฌ์ฉํด๋ผ๊ณ ๋ง๋ StringBuilder๋ฅผ ๋ฐ๋ก ์ ๊ณตํ๋ ๊ฒ์ด๋ค.
์ฐธ๊ณ ๋ก ๋์ฉ๋ ๋ฌธ์์ด ์กฐ์ ์์ ์ ์ฒ๋ฆฌํ๋๋ฐ StrinBuilder๊ฐ 1์ด ๊ฑธ๋ ธ๋ค๊ณ ๊ฐ์ ํ๋ฉด,
- ๋ฉํฐ์ค๋ ๋ ๋๊ธฐํ๋ฅผ ๋ณด์ฅํ๋ StringBuffer๋ 2์ด
- ๊ทธ๋ฅ ์กฐ์ํ ๋๋ง๋ค ๊ฐ์ฒด๋ฅผ ์์ฑํ๋ String์ 2400์ด(40๋ถ)์ ๋ ๊ฑธ๋ฆฐ๋ค.
์ํฉ์ ๋ฐ๋ผ ๋ค๋ฅด๊ฒ ์ง๋ง ์ค์ ํ ์คํธ ํด๋ณด๋ฉด ๋น์ทํ ๊ฒฐ๊ณผ๋ฅผ ๋ณผ ์ ์๋ค. ๊ทธ๋์ JDK1.5๋ถํฐ๋ ์ปดํ์ผ ์์ ์์ String ๋ง์ ์ด StringBuilder๋ก ์๋ ์นํ๋๋ค.
# Java ์ปดํ์ผ๋ฌ์ String ์ต์ ํ
์ค์ ๋ก String๊ณผ StringBuffer๋ ์ฅ๋จ์ ์ด ์์๊ธฐ์ ๊ด๋ จ๋ ๋ ผ์๊ฐ ๋ง์๋ค. ๊ทธ๋์ JDK1.5 ์ดํ ์ปดํ์ผ๋ฌ๋ String ์ฒ๋ฆฌ์ ์์ด ๋ค์๊ณผ ๊ฐ์ ๋ฐ์ดํธ์ฝ๋ ๋ณํ ์ ์ต์ ํ๋ฅผ ๋ณด์ฅํ๋ค.
- ํ์ค์์ ์์ String์ ๋ง์ ์ ์์ ํ ๋ฌธ์์ด๋ก ๋ฐ๊ฟ์ ์ปดํ์ผํ๋ค.
- Java 1.5 ์ดํ์ String ๋ง์ ์ฐ์ฐ์ ์ ๋ถ StringBuilder๋ก ์นํ๋๋ค.
- ์ฆ ํ์ค์์ ์์์ ๋ค๋ฅธ String ํด๋์ค๋ฅผ ๋ํ๋๊ฑด StringBuilder.append() .toString() ๋ฉ์๋๋ก ๋ฐ๊พผ๋ค.
์ค์ ๋ก JDK 1.5๋ฒ์ ์ดํ๋ก๋ ๊ฐ๋ฐ์๊ฐ String๋ง ์ฌ์ฉํ๋๋ผ๋ ์ปดํ์ผ ๋จ๊ณ์์ ์ ์ ํ๊ฒ StringBuffer๋ก ๋ณํํด์ค๋ค.
//๊ธฐ์กด ์๋ฐ์ฝ๋
public static void main(String args[]) {
String str0 = "It's a string....";
String str1 = "It's a string....";
String str2 = "It's a string...." + str0 + "000";
str2 = str0 + str1 + "1111";
str2 = str2 + "1111";
str2 = str2 + "1111";
for (int i = 0; i < 10; i++) {
str2 = str2 + "1111";
str2 = str2 + "1111";
}
}
// jdk1.5 ์ปดํ์ผ๋ฌ๊ฐ ์ต์ ํ ์ํจ ์ฝ๋.
public static void main(String args[]) {
String str0 = "It's a string....";
String str1 = "It's a string....";
String str2 = (new StringBuilder("It's a string....")).append(str0).append("000").toString();
str2 = (new StringBuilder(String.valueOf(str0))).append(str1).append("1111").toString();
str2 = (new StringBuilder(String.valueOf(str2))).append("1111").toString();
str2 = (new StringBuilder(String.valueOf(str2))).append("1111").toString();
for (int i = 0; i < 10; i++) {
str2 = (new StringBuilder(String.valueOf(str2))).append("1111").toString();
str2 = (new StringBuilder(String.valueOf(str2))).append("1111").toString();
}
}
'๐๊ธฐ๋ณธ ์ง์ > Java ๊ธฐ๋ณธ์ง์' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
์๋ฐ ์ด๋ ธํ ์ด์ (@Annotation) (0) | 2021.08.03 |
---|---|
ํ๋ก๊ทธ๋๋ฐ ์ํฐํจํด (Anti-pattern) (0) | 2021.08.02 |
์ฐ๋ ๋ ๋๊ธฐํ (sync, volatile, AtomicClass) (0) | 2021.07.27 |
์๋ฐ์ String๊ณผ Constant Pool (2) | 2021.07.27 |
.equals์ .hashCode()๋ ํญ์ ํจ๊ป ์ค๋ฒ๋ผ์ด๋ฉํด์ผํ๋ค. (0) | 2021.07.27 |
๋ธ๋ก๊ทธ์ ์ ๋ณด
JiwonDev
JiwonDev