285
社区成员




The Link Your Class | https://bbs.csdn.net/forums/MUEE308FZU202201 |
The Link of Requirement of This Assignment | https://bbs.csdn.net/topics/608734907 |
The Aim of This Assignment | output "keyword" statistics |
MU STU ID and FZU STU ID | 20123078-832001301 |
目录
3.Design and implementation process
Personal Software Process Stages | Estimated time(min) | Time(min) |
---|---|---|
Planning | 30 | 25 |
Estimate | 20 | 25 |
Development | 15 | 15 |
Analysis | 130 | 160 |
Design Spec | 50 | 80 |
Design Review | 5 | 5 |
Coding Standard | 90 | 115 |
Design | 70 | 75 |
Coding | 200 | 300 |
Code Review | 50 | 70 |
Test | 25 | 45 |
Test Report | 30 | 40 |
Postmortem & Process Improvement Plan· Design Review | 25 | 30 |
Summary | 740 | 995 |
-When I saw this problem, I thought I could use regular expressions to extract each English letter and then compare it to keywords to get the number of keywords. But I immediately encountered difficulties. If there is a "keyword" in the comments of the file and it does not play a role in that code, that word should not be counted as a keyword. So I decided to preprocess the code first. I used regular expressions to remove anything that interfered with my comments, then used regular expressions again to extract the full English words, match the list of keywords, and record the number of output keywords.
-Next, I use the specific keyword to match the keyword we want so that I can get its number. Of course, this method works when looking for switch keywords and case keywords, I just need to count the total number of case keywords before each switch keyword. Finally, I just had to subtract one by one to get the number of case keywords in each switch case group. But it doesn't work when you're looking for an if-else structure.
-Because the if-else and else, if you still use the original method, you're going to get errors, so I need to use another method to judge them. I decided to use the stack approach to solve this problem. First, I decide if the current keyword is if or else if. If so, I push them onto the stack. When we encounter else, we start judging the stack. If it is If, increment the if-else keyword by 1 and throw it. If it is an else-If, then the else-If keyword increments by 1, throws it and continues until the next one is the if keyword.
# First, read the code and preprocess it
def readcode(path):
string = ''
with open(path, 'r', encoding='UTF-8') as file:
stringline = file.readlines()
for sl in stringline:
string += sl.strip() + ' '
string = re.sub("\"([^\"]*)\"|\/\*([^\*^\/]*|[\*^\/*]*|[^\**\/]*)*\*\/|\/\/.*", "", string)
return string
When the code is finished preprocessing, the number of keywords is counted using regular expressions.
The implementation code is as follows:
# Second, calculate the number of keywords
def countkeywords(string):
cal = {}
caltotal = 0
keywordlist = ['auto', 'break', 'case', 'char', 'const', 'continue', 'default', 'do', 'double', 'else', 'enum',
'extern', 'float', 'for', 'goto', 'if', 'int', 'long', 'register', 'return', 'short', 'signed',
'sizeof', 'static', 'struct', 'switch', 'typedef', 'union', 'unsigned', 'void', 'volatile', 'while']
for keyword in keywordlist:
k = len(re.findall("[^0-9a-zA-Z\_]" + keyword + "[^0-9a-zA-Z\_]", string))
if k != 0:
cal[keyword] = k
caltotal += k
return caltotal
Now, to count the number of switches and the number of cases in each switch case, we also use regular expressions.
The implementation code is as follows:
# Third, calculate the number of switch and the number of case in each switch-case
def countsc(string):
switchnum = 0
casenum = []
switchlist = re.finditer(r"\sswitch\([^)]*\)\s*{", string)
for i in switchlist:
switchnum += 1
index = i.end()
caselist = re.findall(r"\scase\s", string[index:])
casenum.append(len(caselist))
for j in range(switchnum - 1):
casenum[j] = casenum[j] - casenum[j + 1]
return switchnum, casenum
Finally, the stack is used to count the number of if, else, and else if.
The implementation code is as follows:
# Finally, calculate the number of if-else and if-elseif-else
def countifelse(string):
if_stack = []
ifelse_num1 = 0
ifelse_num2 = 0
match_elseif = False
alllist = re.findall(r"else if|\s*else[{\s][^i]|if", string)
for i in range(len(alllist)):
if alllist[i] == "if":
if_stack.append(1)
elif alllist[i] == "else if":
if_stack.append(2)
else:
while True:
if if_stack.pop() == 2:
match_elseif = True
else:
break
if match_elseif:
ifelse_num2 += 1
match_elseif = False
else:
ifelse_num1 += 1
return ifelse_num1, ifelse_num2
Testing code:
import unittest
from keyCount import *
class TestCase(unittest.TestCase):
def test_readfile(self):
path = "./test_read.c"
ans = "int main(){ } "
self.assertEqual(read_file(path), ans)
def test_countkeywords(self):
code = read_file("./test_matchCode.c")
self.assertEqual(countkeywords(code),53)
def test_countswitch(self):
code = read_file("./test_matchCode.c")
self.assertEqual(count_switch(code), (2, [3, 2]))
def test_count_ifelse(self):
code = read_file("./test_matchCode.c")
self.assertEqual(count_ifelse(code), (4, 4))
if __name__ == '__main__':
unittest.main()
Running screenshot:
6.Summary
In this lab, I think I have carefully completed the requirements, considered as much as possible beyond the example I wanted, and dealt with the problem. Regarding the techniques learned in this assignment, I think there are several points:
The Python code
The application of regular expressions
Proficient in GIT and GitHub