2012-04-07 2 views
1

문자열 대신 StringBuilder를 사용하여 이미지에 GDI를 사용하여 문자열을 그릴 수 있습니까? StringBuilder를 허용하는 Graphics.DrawString() 오버로드가 없습니다. 그러나 일반적인 문자열은 경우에 따라 GC 시간을 크게 늘릴 수 있습니다 (내 경우 CLR 프로필러에 따라 52 %).StringBuilder를 사용하여 C# GDI + DrawString()?

참고 : 4.0 이후의 StringBuilder를 지원하는 XNA Framework는 사용하고 싶지 않습니다.

+7

StringBuilder는 문자열을 "빌드"하는 데 유용합니다. 일단 빌드하면 stringbuilder와 string은 동일한 성능을 갖습니다. 따라서 stringbuilder를 전달하면 DrawString (전체 문자열이 필요함)의 성능을 향상시킬 수있는 방법을 알 수 없습니다. 그럼, 내 대답은 : StringBuilder를 사용하여 문자열을 작성한 다음, myStringBuilder.ToString()을 'DrawString()' – digEmAll

+0

@digEmall에 동의하면 stringbuilder와 문자열의 관점에서 스틱의 잘못된 끝을 파악한 것 같습니다. –

+0

+1 for @digEmAll, StringBuilder 값을 필요로 할 때 .ToString()을 호출하도록 남겨 두는 문자열을 생성합시다. –

답변

0

대체 그래픽 라이브러리를 사용하지 않고서 가능하다고 생각하지 않습니다.

이후 .NET 4.0, StringBuildernot use a String class internally (반사 되어도 String 개체를 추출 할 수 없음).

myStringBuilder.ToString()을 호출하면 성능이 저하됩니다. 그것은 본질적으로 그것이 호출 될 때마다 당신의 문자열의 사본을 만들고 있습니다. 그러나 Graphics.DrawString()을 호출하는 코드에서 병목 현상이 발생하지는 않습니다.

+0

제 질문에 대한 대답은 슬프게도 "불가능합니다"라는 말을 따르는 것입니다. .ToString() 자체는 병목 현상이 아닙니다. 그러나 그것이 할당하는 쓰레기는 있습니다. 구형 시스템에서는 .NET의 GC가 일부 용도에 적합하지 않기 때문에 fps가 완전히 소모됩니다. 다시 말하지만 ToString()은 없지만 50 개는 될 수 있습니다. 그 x60/초는 3000x 쓰레기/초입니다. GC가 ~ 1MB에 도달하면 Collect()가 될 것이고 너무 많은 참조가 있으면 분할 순간에 fps가 유출됩니다. 이런 일이 너무 많이 발생하면 무엇을하더라도 항상 fps가 소모됩니다. – Napoleon

+0

가끔은 미리 문자열을 할당 할 수 있습니다. 그러나 지금까지는 그렇지 않습니다. 이것을 해킹 할 수있는 몇 가지 방법이 있지만 단순한 빌드 인 (build-in) 솔루션이나 다른 것을 기대하고 있습니다. – Napoleon

+0

@Napoleon .NET GC가이 경우 응용 프로그램의 FPS에 눈에 띄는 영향을 미치지는 않을 것이라고 생각합니다. 이러한 임시 문자열은 반드시 [generation 0] (http://msdn.microsoft.com/en-us/library/ee787088.aspx#generations) 개체가되고 가비지 수집의 재배치 및 압축 단계가 적용되지 않습니다. 가장 큰 성능 히트는 문자열을 생성 할 때 발생합니다 (메모 : 메모리 할당/할당 해제에는 비용이 들지 않습니다). 가비지 콜렉션의 마킹 단계에서 시간이 많이 걸릴 것이지만, FPS의 차이점 –