如何统计一个JAVA项目中的代码行数?

rainight 2004-10-09 08:58:10
有没有此类的工具可以推荐一下
...全文
1121 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
zez 2004-10-09
  • 打赏
  • 举报
回复
hehe,培训时写的...
应用不方便......很多其他培训的学员写了很多功能强大的.不过我手里没有:(
zez 2004-10-09
  • 打赏
  • 举报
回复
/**
* 计算一行中的逻辑代码行
* 基本法:计算代码行中的 ; 和 { 的个数
* 缺陷: 现在无法对注释中的 ; 和 { 情况进行剔除 (//后面的注释和 块注释尾标志所在行的注释)
* 有兴趣的话来完成吧:)
* 做完了最好给我发一份过来 .OK
* @param str
*/
/* private void countLogicLineNum(String str)
{
String aStr = str;
while(aStr.indexOf( ";")>0 && isNotInStr(aStr,";"))
{
logicLineNum++;
aStr = aStr.substring( aStr.indexOf( ";")+1);
}
aStr = str;
while(aStr.indexOf( "{")>=0)
{
logicLineNum++;
aStr = aStr.substring( aStr.indexOf( "{")+1);
}

}**/
/**
* 打印计算结果
*
*/
private void printResult() {

int codeLineNum = totalLineNum - blankLineNum - commentLineNum;
System.out.println("总行数为 : " + totalLineNum);
System.out.println("代码行数为 : " + codeLineNum);
System.out.println("总注释行数为 : "
+ (commentLineNum + codeAndCommentLinNum));
System.out.println("空行数为 : " + blankLineNum);
System.out.println("混合行数为 : " + codeAndCommentLinNum);
System.out.println("纯注释行数为 : " + commentLineNum);
System.out.println("注释中空行数为: " + blankAndCommentLinNum);
// System.out.println("逻辑代码行数为 : " + logicLineNum);
int commentRat ;
if((commentLineNum + codeAndCommentLinNum)==0 || totalLineNum==0 )
{
commentRat = 0;
}else{
commentRat = (100 * (commentLineNum + codeAndCommentLinNum) / totalLineNum);
}
System.out.println("注释率为 : "
+ commentRat
+ "%");
}

/**
* 打印计算结果
*
*/
private void printTotalResult() {

int gcodeLineNum = gtotalLineNum - gblankLineNum - gcommentLineNum;
System.out.println("总行数为 : " + gtotalLineNum);
System.out.println("代码行数为 : " + gcodeLineNum);
System.out.println("总注释行数为 : "
+ (gcommentLineNum + gcodeAndCommentLinNum));
System.out.println("空行数为 : " + gblankLineNum);
System.out.println("混合行数为 : " + gcodeAndCommentLinNum);
System.out.println("纯注释行数为 : " + gcommentLineNum);
System.out.println("注释中空行数为: " + gblankAndCommentLinNum);
// System.out.println("逻辑代码行数为 : " + logicLineNum);
int commentRat ;
if((gcommentLineNum + gcodeAndCommentLinNum)==0 || gtotalLineNum==0 )
{
commentRat = 0;
}else{
commentRat = (100 * (gcommentLineNum + gcodeAndCommentLinNum) / gtotalLineNum);
}
System.out.println("注释率为 : " + commentRat+ "%");
}
/**
* 统计结果汇总
*
*/
private void countTotalNum(){
gcommentLineNum += commentLineNum ;
gcodeAndCommentLinNum += codeAndCommentLinNum;
gblankLineNum += blankLineNum;
gtotalLineNum += totalLineNum;
gblankAndCommentLinNum += blankAndCommentLinNum;
}
/**
* 嵌套计算文件夹内所有文件
* @param fileName //文件或目录名
* @throws Exception
*/
private void count(String fileName) throws Exception {
try {
File file = getSourceFile(fileName);
if (null != file) {
if (file.isFile()) {
System.out.println("\n源文件: " + fileName + " 统计信息为: ");
init();
openFile(file);
countLineNum();
printResult();
countTotalNum();
} else if (file.isDirectory()) {
String[] fNameList = file.list();
for (int i = 0; i < fNameList.length; i++) {
count(fileName + "\\" + fNameList[i]);
}
}
}
} catch (Exception e) {
throw e;
}
}

public static void main(String[] args) {
try {
String fileName;
if (args == null || args.length == 0) {
System.out.println("请输入要统计的文件或目录:\n");
byte[] buff = new byte[255];
System.in.read(buff);
fileName = new String(buff).trim();

} else {
fileName = args[0];
}
// fileName = "c:\\test";

Clog clog = new Clog();
long begin = System.currentTimeMillis() ;
clog.count(fileName);
if(new File(fileName).isDirectory() ){
System.out.println("目录 "+fileName+" 下所有源文件统计汇总如下:\n") ;
clog.printTotalResult() ;
}
long end = System.currentTimeMillis() ;
System.out.println("\n 用时: "+(end-begin)+" 毫秒 .") ;
} catch (Exception e) {
if(null==e.getMessage() || e.getMessage().trim() .length() ==0){
System.out.println(" 系统出错,错误信息为 :\n") ;
e.printStackTrace() ;
}else{
System.out.println(" 程序出错,错误信息为 :\n " + e.getMessage());
}
}
}
}
zez 2004-10-09
  • 打赏
  • 举报
回复
package com.huawei.sw1.clog;

import java.io.File;
import java.io.FileReader;
import java.io.LineNumberReader;
import java.io.IOException;

/**
* @author zez
*
* 源文件代码行统计工具Java版 :)
*/
public class Clog {

//多文件代码统计汇总结果
private int gcommentLineNum = 0;

private int gcodeAndCommentLinNum = 0;

private int gblankLineNum = 0;

private int gtotalLineNum = 0;

private int gblankAndCommentLinNum = 0;


//单个文件统计信息
private LineNumberReader lReader;

private int commentLineNum = 0;

private int codeAndCommentLinNum = 0;

private int blankLineNum = 0;

private int totalLineNum = 0;

private int blankAndCommentLinNum = 0;

// private int logicLineNum = 0;

//初始化
private void init() {
lReader = null;
commentLineNum = 0;
codeAndCommentLinNum = 0;
blankLineNum = 0;
totalLineNum = 0;
blankAndCommentLinNum = 0;
// logicLineNum = 0;
}

/**
* 判断文件类型,并取得此文件
*
* @param fileName
* @return file, if not a source code file, return NULL .
*/
private File getSourceFile(String fileName) {
if (fileName == null || fileName.trim().length() == 0) {
System.out.println("\nThe file name /* is null !\n");
return null;
}
File file = new File(fileName);
// 如果是目录,返回此目录
if (file.isDirectory()) {
return file;
}
//文件是否存在
if (!file.exists()) {
System.out.println("\nThe file " + fileName
+ " is don't exists !\n");
return null;
}

/**
* 判断是否是.c .cpp .java文件
*/
if (fileName.indexOf('.') > 0) {
String fileExt = fileName.substring(fileName.lastIndexOf('.') + 1).toLowerCase();
if (!fileExt.equals("c") && !fileExt.equals("cpp") && !fileExt.equals("h")
&& !fileExt.equals("java")&& !fileExt.equals("hpp")) {

System.out.println("\nThe file " + fileName
+ " is not a C or C++ or JAVA source file !\n");
return null;

}
}

//文件大小是否大于64k,不过大于64k仍可以计算
if (file.length() > 65535) {
System.out.println("\nThe file " + fileName
+ " is too large than 64k ,but It can work :)!\n");
}
//文件大小如果小于3个字节,返回空
if (file.length() < 3) {
System.out.println("\nThe file " + fileName
+ " has no content \n");
return null;
}

return file;
}

/**
* 打开文件
* @param file
* @throws Exception
*/
private void openFile(File file) throws Exception {
try {
lReader = new LineNumberReader(new FileReader(file));
} catch (Exception e) {
throw e;
}
}

/***************************************************************************
* 行数计算主函数 算法: 循环每次读取一行,分几种情况进行计算 1.空行 2.//开头 肯定为注释行 3.//在代码后面,
* 按代码行算,并处理//在字符串中情况 4.以/*开头的情况,调用专门块注释计算方法 5./* 在代码后面情况,处理同上
*
*/

private void countLineNum() throws Exception {

try {
while (true) { //未到文件尾
String str = lReader.readLine(); //取得一行代码

totalLineNum++; //总行数加一

if (str == null) { //判断是否为文件尾

totalLineNum--;
return;
} else { //否则进行计算
str = str.trim(); //去两头空格
// countLogicLineNum(str);
if (str.length() == 0) { //如果为空,则为空行,空行数加一
blankLineNum++;

} else if (str.startsWith("//")) { //如果是以//开头,为注释行,即使此行有//注释,但非开头,则要按代码行算
commentLineNum++;

} else if (str.indexOf("//") > 0 && isNotInStr(str, "//")) { // //在行中,并判断不是在字符串中
codeAndCommentLinNum++;
} else if (str.indexOf("/*") >= 0) {
//如果/*在行中,判断是否是在""内 ,否则为注释行
if (isNotInStr(str, "/*")) {
countCommentLin(str);//计算/**/ 内的注释行数
}
}
}
}
} catch (IOException e) {
throw new Exception("文件读取时出错 !\n");
}
}

/**
* 块注释计算方法 判断是否块注释结束 否则读下一行 循环
*/
private void countCommentLin(String str) throws Exception {
try {
commentLineNum++;
//处理 /*some comment */ 即只一行的情况,并处理 /*/ 这种情况
if((str.substring( str.indexOf( "/*")+2).indexOf( "*/")>=0)){
//是否有代码
if(str.length() > str.indexOf( "*/")-str.indexOf( "/*")){
codeAndCommentLinNum++;
commentLineNum--;
// countLogicLineNum(str);
}
//处理 /*xxx*/ some code /* 这种情况
if(str.lastIndexOf( "*/")>str.lastIndexOf( "/*")+1)
{
// countLogicLineNum(str);
return;
}
}
//一般情况, some code /* some comment
if(str.indexOf( "/*")>0){
codeAndCommentLinNum++;
commentLineNum--;
}

do {
str = lReader.readLine(); //不是注释尾,取下一行代码
totalLineNum++;
//如果到文件尾,返回
if (str == null) {
totalLineNum--;
return;
}
str = str.trim(); //去空格
//是否到注释尾,如果后面还有代码,按混合行算
if (str.indexOf("*/") >= 0) {
commentLineNum++;
if (str.length() > str.indexOf("*/") + 2) {
codeAndCommentLinNum++;
commentLineNum--;
// countLogicLineNum(str);
}
return;
} else {
if (str.length() == 0) { //是空行
blankLineNum++; //空行加一
blankAndCommentLinNum++; //注释中空行加一
} else {
commentLineNum++; //注释加一
}
}
} while (true);

} catch (IOException e) {
throw new Exception("文件读取时出错 !\n");
}
}

/*
* 判断 某字符 是否是字符串中,特别注释字符. 算法 : 字符串中是否有注释符号 如没有,返回 false 字符串中有 "
* ,如没有,返回true 注释符号在""之前,返回true;否则,继续 str = str的非\"的"后面部分 循环
*/
private boolean isNotInStr(String str, String subStr) {

while (str.indexOf(subStr) >= 0) {
if (str.indexOf('"') >= 0) {
if (str.indexOf('"') > str.indexOf(subStr)) {
return true;
} else {
str = str.substring(str.indexOf('"') + 1);

while (str.indexOf('\\') >= 0
&& str.indexOf('"') == str.indexOf('\\') + 1) {
str = str.substring(str.indexOf('"') + 1);
}
str = str.substring(str.indexOf('"') + 1);
}
} else {
return true;
}
}
return false;
}
项目使用的技术: 1、前端:jsp、css、javascript、jQuery(js框架)、jquery.form.js、HTML富文本编辑器、        My97时间控件(添加员工)2、后台:Struts2、动态代理、Mybatis框架、log4J日志框架、jstl 、jstl自定义分页标签、代码机器人、Dwr、POI(实现Excel文件的导入导出)等3、数据库:Mysql4、服务器:Tomcat项目涉及的功能: 1、项目以及数据库搭建2、用户异步登录、退出3、拦截器功能实现以及整合动态代理4、公告模块的增加、修改、删除、查询以及预览功能实现、文件异步上传5、文档模块的增加、修改、删除、查询以及文档的上传下载6、员工信息的增加、修改、删除、查询以及员工头像异步上传、员工信息导出至Excel文件7、自定义分页标签实现(24种样式随意切换)8、代码机器人使用等等其他实战项目java项目实战之电商系统全套(前台和后台)(java毕业设计ssm框架项目)https://edu.csdn.net/course/detail/25771 java项目之oa办公管理系统(java毕业设计)https://edu.csdn.net/course/detail/23008 java项目之hrm人事管理项目java毕业设计)https://edu.csdn.net/course/detail/23007 JavaWeb项目实战之点餐系统前台https://edu.csdn.net/course/detail/20543 JavaWeb项目实战之点餐系统后台https://edu.csdn.net/course/detail/19572 JavaWeb项目实战之宿舍管理系统(Java毕业设计含源码)https://edu.csdn.net/course/detail/26721 JavaWeb项目实战之点餐系统全套(前台和后台)https://edu.csdn.net/course/detail/20610 java项目实战之电子商城后台(java毕业设计SSM框架项目)https://edu.csdn.net/course/detail/25770 java美妆商城项目|在线购书系统(java毕业设计项目ssm版)https://edu.csdn.net/course/detail/23989 系统学习课程:JavaSE基础全套视频(环境搭建 面向对象 正则表达式 IO流 多线程 网络编程 java10https://edu.csdn.net/course/detail/26941 Java Web从入门到电商项目实战挑战万元高薪(javaweb教程)https://edu.csdn.net/course/detail/25976其他素材版(毕业设计或课程设计)项目:点击老师头像进行相关课程学习
可用于对VC++、C++ Builder、Delphi、VB、C/C++、ASM、Java、C#、SQL 等程序源码进行详细的统计,可以准确的分析出程序代码行、注释行和空白行的行数。程序会自动根据你选择的文件类型选择相应的统计方式,并将所有文件的分析结果进行汇总,便于方便直观的对软件项目代码量进行全面的评估。本软件是绿色软件,不需要安装,展开到任意目录,直接运行即可。 1、 支持VC++项目文件的统计方式。 2、 支持C++ Builder项目文件的统计方式。 3、 支持C/C++文件 .cpp 和 .h 的文件统计。 4、 支持同时多个文件的统计方式。 5、 支持同时多种文件类型的统计方式。 6、 支持VB项目文件和 .frm 和 .bas 文件的统计。 7、 支持汇编文件 .asm 和 .inc 的统计。 8、 支持Delphi项目文件 .dpr 和 .pas、.dfm 文件的统计。 9、 支持C#项目文件 .csproj 的直接统计及 .cs 文件的统计。 10、支持Java文件 .java统计。 11、支持SQL文件 .sql 的统计。 12、支持 *.* 文件类型的自动分析统计。 13、支持文件目录的选择统计方式。 14、支持用户自定义文件统计类型及统计方法。 15、支持Htm,Excel,Csv,Txt等多种存盘文件类型。 16、支持统计结果的直接打印输出。 17、支持命令行方式的文件及目录统计方式。 18、支持资源管理器右键关联的文件及目录快捷统计方式。

67,512

社区成员

发帖
与我相关
我的任务
社区描述
J2EE只是Java企业应用。我们需要一个跨J2SE/WEB/EJB的微容器,保护我们的业务核心组件(中间件),以延续它的生命力,而不是依赖J2SE/J2EE版本。
社区管理员
  • Java EE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧