클린코드
카테고리 미분류
지은이 로버트 C. 마틴 (케이앤피IT, 2010년)
상세보기


import java.io.BufferedReader;
import java.io.File;
import java.util.List;
import java.util.Set;

public class CodeAnalyzer {
	private int lineCount;
	private int maxLineWidth;
	private int widestLineNumber;
	private LineWidthHistogram lineWidthHistogram;
	private int totalChars;

	public CodeAnalyzer() {
		lineWidthHistogram = new LineWidthHistogram();
	}
	
	public static List<File> findJavaFiles(File parentDirectory) {
		List<File> files = new ArrayList<File>();
		findJavaFiles(parentDirectory, files);
		return files;
	}
	
	public static void findJavaFiles(File parentDirectory, List<File> files) {
		for(File file : parentDirectory.listFiles()) {
			if (file.getName().endsWith(".java"))
				files.add(file);
			else if (file.isDirectory())
				findJavaFiles(file, files);
		}
	}
	
	public vvoid analyzeFile(File javaFile) throws Exception {
		BufferedReader br = new BufferedReader(new FileReader(javaFile));
		String line;
		while ((line = br.readLine()) != null)
			measureLine(line);
	}
	
	private void measureLine(String line) {
		lineCount++;
		int lineSize = line.length();
		totalChars += lineSize;
		lineWidthHistogram.addLine(lineSize, lineCount);
		recordWidestLine(lineSize);
	}
	
	private void recordWidestLine(int lineSize) {
		if (lineSize > maxLineWidth) {
			maxLineWidth = lineSize;
			widestLineNumber = lineCount;
		}
	}
	
	public int getLineCount() {
		return lineCount;
	}
	
	public int getMaxLineWidth() {
		return maxLineWidth;
	}
	
	public int getWidestLineNumber() {
		return widestLineNumber;
	}
	
	public LineWidthHistogram getLineWidthHistogram() {
		return lineWidthHistogram;
	}
	
	public double getMeanLineWidth() {
		return (double)totalChars/lineCount;
	}
	
	public int getMedianLineWidth() {
		Integer[] sortedWidths = getSortedWidths();
		int cumulativeLineCount = 0;
		for (int width : sortedWidths) {
			cumulativeLineCount += lineCountForWidth(width);
			if (cumulativeLineCount > lineCount)
				return width;			
		}
		throws new Error("Cannot get here");
	}
	
	private int lineCountForWidth(int width) {
		return lineWidthHistogram.getLinesforWidth(width).size();
	}
	
	private Integer[] getSortedWidth() {
		Set<Integer> widths = lineWidthHistogram.getWidths();
		Integer[] sortedWidths = (widths.toArray(new Integer[0]));
		Arrays.sort(sortedWidths);
		return sortedWidths;
	}
	
}


클린코드
카테고리 미분류
지은이 로버트 C. 마틴 (케이앤피IT, 2010년)
상세보기


public class SetupTeardownIncluder {

	private PageData pageData;
	private boolean isSuite;
	private WikiPage testPage;
	private StringBuffer	newPageContent;
	private PageCrawler pageCrawler;
	
	public static String render(PageData pageData) throws Exception {
		return render(pageData, false);
	}
	
	public static String render(PageData pageData, boolean isSuite) throws Exception {
		return new SetupTeardownIncluder(pageData).render(isSuite);
	}
	
	private SetupTeardownIncluder(PageData pageData) {
		this.pageData = pageData;
		testPage = pageData.getWikiPage();
		pageCrawler = testPage.getPageCrawler();
		newPageContent = new StringBuffer();
	}
	
	private String render(boolean isSuite) throws Exception {
		this.isSuite = isSuite;
		if (isTestPage())
			includeSetupAndTeardownPages();
		return pageData.getHtml();
	}
	
	private boolean isTestPage() throws Exception {
		return pageData.hasAttribute("Test");
	}
	
	private void includeSetupAndTeardownPages() throws Exception {
		includeSetupPages();
		includePageContent();
		includeTeardownPages();
		updatePageContent();
	}
	
	private void includeSuiteSetupPage() throws Exception {
		include(SuiteResponder.SUITE_SETUP_NAME, "-setup");		
	}
	
	private void includeSetupPage() throws Exception {
		include("Setup", "-setup");		
	}
	
	private void includePageContent() throws Exception {
		newPageContent.append(pageData.getContent());
	}
	
	private void includeTeardownPages() throws Excepton {
		includeTeardownPage();
		if (isSuite)
			includeSuiteTeardownPage();
	}
	
	private void includeTeardownPage() throws Exception {
		include("TearDown", "-teardown");
	}
	
	private void includeSuiteTeardownPage() throws Exception {
		include(SuiteResponder.SUITE_TEARDOWN_NAME, "-teardown");
	}
	
	private void updatePageContent() throws Exception {
		pageData.setContent(newPageContent.toString());
	}
	
	private void include(String pageName, String arg) throws Exception {
		WikiPage inheritedPage = findInheritedPage(pageName);
		if ( inheritedPage != null ) {
			String pagePathName = getPathNameForPage(inheritedPage);
			buildIncludeDirective(pagePathName, arg);
		}
	}
	
	private WikiPage findInheritedPage(String pageName) throws Exception {
		return PageCrawlerImpl.getInheritedPage(pageName, testPage);
	}
	
	private String getPathNameForPage(WikiPage page) throws Exception {
		WikiPagePath pagePath = pageCrawler.getFullPath(page);
		return PathParser.render(pagePath);
	}
	
	private void buildIncludeDirective(String pagePathName, String arg) {
		newPageContent
			.append("\n!include ")
			.append(arg)
			.append(" .")
			.append(pagePathName)
			.append("\n");
	}
}
지난 TDD 강의 시간에 미처 못풀었던 소수구하기 문제를 풀어본다. 뭐, 이러면서 자바에 대한 감을 살려가는거 아니겠어?? +_+)


-- 실행결과 : 5 에서 10000 사이의 소수 구하기

확실히... 숫자를 키울수록 연산 속도는 오래 걸리는구나. +_+)

기능을 구현하는 방법은 참 여러가지다. 이것이 옳고 저것이 옳다라고 말하기는 어렵다.

뭐 그렇다. ㅎㅎ.

이 소스를 TDD로 적용하면 어떻게 될까나? ^^; 어떤 테스트 시나리오조건을 만들어서 만들어야 할까나?
- 소스의 가독성이 적절한가?
- 중복된 코드는 없는가?
- 이름이 잘못 부여된 메소드나 변수명은 없는가?
- 구조의 개선이 필요한 부분은 없는가?

리팩토링에 대해서 조금씩 알아가고 있는 상황....

+ Recent posts