StringAutoTest.swift 35 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642
  1. //
  2. // CharacterAutoTest.swift
  3. // KdanAuto
  4. //
  5. // Created by 朱东勇 on 2022/11/22.
  6. //
  7. import Foundation
  8. import Cocoa
  9. class StringAutoTest : AutoTest {
  10. // override func type() -> String {
  11. // return "PDFConvert_China_Auto_Test"
  12. // }
  13. override func name() -> String {
  14. return _name
  15. }
  16. override func keys() -> NSArray {
  17. return ["字符"]
  18. }
  19. override func needTest() -> Bool {
  20. return self.selectedKeys().count > 0
  21. }
  22. override class func shared() -> AutoTest? {
  23. return StringAutoTest()
  24. }
  25. // Auto Test refrence Check File
  26. override func autoTest(_ complention:@escaping (_ object:AutoTest, _ report:NSAttributedString?) -> ()) {
  27. self.compareFinishedFiles.removeAllObjects();
  28. self.convertFiles.removeAllObjects()
  29. clearCacheFiles()
  30. let needCheckString = self.selectedKeys().contains("字符")
  31. if !needCheckString {
  32. _status = .Finished
  33. complention(self, self.reportString)
  34. return
  35. }
  36. _status = .Process
  37. reportString = NSMutableAttributedString.init(string: "\n【\(String(self.fileType())) - \(self.name())】字符比对开始!\n",
  38. attributes:[.foregroundColor : NSColor.blue])
  39. let files = DataModel.shared.originFilesFor(_fileType, type: _type)
  40. self.testFiles = NSArray(array: files);
  41. let checkDirectory = self.checkFileDirectory()
  42. let originDirectory = self.originFileDirectory()
  43. let resultDirectory = self.resultFileDirectory()
  44. if (files.count > 0) {
  45. try? FileManager.default.createDirectory(atPath: checkDirectory, withIntermediateDirectories: true);
  46. try? FileManager.default.createDirectory(atPath: resultDirectory, withIntermediateDirectories: true);
  47. }
  48. var tDegree = Double(0);
  49. var tCount = Int(0)
  50. var fileIndex = 0;
  51. var convertFileBlock = { (files:[String]) in }
  52. convertFileBlock = { (files:[String]) in
  53. if (fileIndex >= files.count) {
  54. TestDegreeManager.shared().set(((tCount != 0) ? tDegree/Double(tCount) : 0.0),
  55. fileType: self.fileType(),
  56. type: self.type())
  57. self._status = .Finished
  58. DispatchQueue.main.async {
  59. autoreleasepool {
  60. complention(self, self.reportString);
  61. }
  62. }
  63. return
  64. }
  65. let fileName = files[fileIndex]
  66. let fName = NSString(string: fileName).deletingPathExtension
  67. let originPath = NSString(string: originDirectory).appendingPathComponent(fName+".pdf")
  68. let resultPath = NSString(string: resultDirectory).appendingPathComponent(fName+"."+self.extention())
  69. let checkPath = NSString(string: checkDirectory).appendingPathComponent(fName+"."+self.extention())
  70. self.reportString?.append(NSMutableAttributedString.init(string: "\n【\(String(self.fileType())) - \(self.name())】开始转换文件 \"\(fName)\"\n",
  71. attributes:[.foregroundColor : NSColor.black]))
  72. // ...
  73. // 执行转换过程
  74. let index = self.testFiles.index(of: fileName);
  75. if (index != NSNotFound) {
  76. self.convertProgress = Double(index) / Double(self.testFiles.count)
  77. }
  78. self.convertFiles.add(fileName);
  79. self.testlog("开始转换:"+fileName, (self.compareProgress + self.convertProgress)/2.0)
  80. self.process(originPath, resultPath: resultPath) { status in
  81. if FileManager.default.fileExists(atPath: resultPath) && status == 1 {
  82. if needCheckString && FileManager.default.fileExists(atPath: checkPath) {
  83. DispatchQueue.global().async {
  84. let checkString = self.readTextFile(checkPath as NSString)
  85. let resultStr = self.readTextFile(resultPath as NSString)
  86. if (checkString != nil && resultStr != nil) {
  87. let maxSize = checkString!.count
  88. let report = NSMutableAttributedString(string: "")
  89. let degree = self.compareString(checkString as! NSString, result: resultStr as! NSString) { appAttr in
  90. report.append(appAttr)
  91. }
  92. // let degree = self.compareString(checkString as! NSString, result: resultStr as! NSString) { skipString, failString in
  93. // self.appendErrorInfo(skipString, failString: failString)
  94. // }
  95. var color = NSColor.black
  96. if fabs(degree-100.0) >= 0.01 {
  97. color = NSColor.red
  98. }
  99. tDegree += degree;
  100. tCount += 1
  101. TestDegreeManager.shared().set(degree,
  102. fileType: self.fileType(),
  103. type: self.type(),
  104. fileName: fileName)
  105. let successCount = Int(maxSize * Int(degree)/100)
  106. report.append(NSAttributedString.init(string: "\n【\(String(self.fileType())) - \(self.name())】文件 \"\(fName)\"比对完成,准确率\(degree)%(\(successCount)/\(maxSize))\n",
  107. attributes:[.foregroundColor : color]))
  108. if (report != nil) {
  109. do {
  110. let rtfData = try? report.data(from: .init(location: 0, length: report.length),
  111. documentAttributes: [.documentType: NSAttributedString.DocumentType.rtf])
  112. let path = NSString(string: resultPath).appendingPathExtension("rtf")
  113. try? FileManager.default.removeItem(atPath: path!);
  114. try? rtfData?.write(to: NSURL.fileURL(withPath: path!))
  115. } catch {
  116. }
  117. self.reportString?.append(report)
  118. }
  119. }
  120. let index = self.testFiles.index(of: fileName);
  121. if (index != NSNotFound) {
  122. self.compareProgress = Double(index) / Double(self.testFiles.count)
  123. }
  124. self.compareFinishedFiles.add(fileName);
  125. self.testlog("对比完成:"+fileName, (self.compareProgress + self.convertProgress)/2.0)
  126. fileIndex += 1
  127. convertFileBlock(files);
  128. }
  129. }else {
  130. self.reportString?.append(NSMutableAttributedString.init(string: "【\(String(self.fileType())) - \(self.name())】对照文件 \"\(fName)\"不存在!\n",
  131. attributes:[.foregroundColor : NSColor.red]))
  132. let index = self.testFiles.index(of: fileName);
  133. if (index != NSNotFound) {
  134. self.compareProgress = Double(index) / Double(self.testFiles.count)
  135. }
  136. self.compareFinishedFiles.add(fileName);
  137. self.testlog("对比完成:"+fileName, (self.compareProgress + self.convertProgress)/2.0)
  138. fileIndex += 1
  139. convertFileBlock(files);
  140. }
  141. }else {
  142. if (status == 0) {
  143. self.reportString?.append(NSMutableAttributedString.init(string: "【\(String(self.fileType())) - \(self.name())】文件 \"\(fName)\"转档失败!\n",
  144. attributes:[.foregroundColor : NSColor.red]))
  145. }else if (status == -1 || status == -2) {
  146. self.reportString?.append(NSMutableAttributedString.init(string: "【\(String(self.fileType())) - \(self.name())】文件 \"\(fName)\"文档无法打开!\n",
  147. attributes:[.foregroundColor : NSColor.red]))
  148. }else if (status == -3) {
  149. self.reportString?.append(NSMutableAttributedString.init(string: "【\(String(self.fileType())) - \(self.name())】文件 \"\(fName)\"转档中 Crash!\n",
  150. attributes:[.foregroundColor : NSColor.red]))
  151. }
  152. let index = self.testFiles.index(of: fileName);
  153. if (index != NSNotFound) {
  154. self.compareProgress = Double(index) / Double(self.testFiles.count)
  155. }
  156. self.compareFinishedFiles.add(fileName);
  157. self.testlog("对比完成:"+fileName, (self.compareProgress + self.convertProgress)/2.0)
  158. fileIndex += 1
  159. convertFileBlock(files);
  160. }
  161. }
  162. }
  163. convertFileBlock(files);
  164. }
  165. ///Compare
  166. /// Tools
  167. func appendErrorInfo(_ skipString:NSString, failString: NSString) {
  168. if skipString.length > 0 && failString.length > 0 {
  169. reportString?.append(NSMutableAttributedString.init(string: "对比字符串【\(skipString)】错识别为【\(failString)】\n",
  170. attributes:[.foregroundColor : NSColor.red]))
  171. }else if (skipString.length > 0) {
  172. reportString?.append(NSMutableAttributedString.init(string: "对比字符串【\(skipString)】未识别到\n",
  173. attributes:[.foregroundColor : NSColor.red]))
  174. }else if failString.length > 0 {
  175. reportString?.append(NSMutableAttributedString.init(string: "字符串【\(failString)】识别出错\n",
  176. attributes:[.foregroundColor : NSColor.red]))
  177. }
  178. }
  179. func attributeStringWith(_ skipString:NSString, failString: NSString) -> NSAttributedString {
  180. if skipString.length > 0 && failString.length > 0 {
  181. let strikethroughStyle = NSParagraphStyle.init()
  182. let attString = NSMutableAttributedString.init(string: skipString as String,
  183. attributes:[.foregroundColor : NSColor.red,
  184. .strikethroughStyle:NSNumber(integerLiteral: NSUnderlineStyle.single.rawValue),
  185. ])
  186. attString.append(NSMutableAttributedString.init(string: failString as String,
  187. attributes:[.foregroundColor : NSColor.blue,
  188. ]))
  189. return attString
  190. }else if (skipString.length > 0) {
  191. let strikethroughStyle = NSParagraphStyle.init()
  192. let attString = NSMutableAttributedString.init(string: skipString as String,
  193. attributes:[.foregroundColor : NSColor.red,
  194. .strikethroughStyle:NSNumber(integerLiteral: NSUnderlineStyle.single.rawValue),
  195. ])
  196. return attString
  197. }else if failString.length > 0 {
  198. let strikethroughStyle = NSParagraphStyle.init()
  199. let attString = NSMutableAttributedString.init(string: failString as String,
  200. attributes:[.foregroundColor : NSColor.blue,
  201. ])
  202. return attString
  203. }
  204. return NSAttributedString()
  205. }
  206. func replaceUnicodeString(_ string:NSString) -> NSString {//中
  207. let items = string.components(separatedBy: "\\u") as [NSString]
  208. var resultString = NSString()
  209. for item in items {
  210. if (item.contains("?")) {
  211. let unicodeValue = item.intValue
  212. let skipRange = item.range(of: "?")
  213. let nextString = item.substring(from: Int(skipRange.location + skipRange.length)) as NSString
  214. let bytes : [UInt8] = [UInt8(unicodeValue/256),UInt8(unicodeValue%256)]
  215. let data = NSData.init(bytes: bytes, length: 2)
  216. let unicodeString = NSString.init(data: data as Data, encoding: NSUnicodeStringEncoding)! as NSString
  217. resultString = resultString.appending(String("\(unicodeString)\(nextString)")) as NSString
  218. }else {
  219. resultString = resultString.appending(String(item)) as NSString
  220. }
  221. }
  222. return resultString
  223. }
  224. /// Compare
  225. func compareString(_ check:NSString, result:NSString, callback:@escaping (_ appAttr:NSAttributedString)->()) -> Double {
  226. // func compareString(_ check:NSString, result:NSString, failure:@escaping (_ skipString:NSString, _ failString:NSString)->()) -> Double {
  227. return autoreleasepool {
  228. var checkString = check
  229. var resultStr = result
  230. var maxSize = checkString.length
  231. var successCount = 0;
  232. resultStr = resultStr.replacingOccurrences(of: "\n", with: "") as NSString
  233. resultStr = resultStr.replacingOccurrences(of: " ", with: "") as NSString
  234. /**
  235. (A0 = B0)
  236. - A-1 & B-1
  237. (A0 != B0) & (A0 in B) & (B0 in A)
  238. - 取 A0,B0最小 Range 值
  239. - 字符串裁剪对齐
  240. (A0 != B0) & (A0 in B)
  241. - 存储B0到识别错误缓存
  242. (A0 != B0) & (B0 in A)
  243. - 存储 A0到识别遗漏字符串
  244. (A0 != B0)
  245. - 分别存储 A0、B0到遗漏及错误字串
  246. */
  247. var skipString = NSString()
  248. var failString = NSString()
  249. while (checkString.length > 0 && resultStr.length > 0) {
  250. let subc = checkString.substring(to: 1) as NSString
  251. let subr = resultStr.substring(to: 1) as NSString
  252. let cRange = checkString.range(of: subr as String)
  253. let rRange = resultStr.range(of: subc as String)
  254. if subc.isEqual(to: subr) { // (A0 = B0)
  255. // Check Success
  256. // 两个字符相同
  257. callback(attributeStringWith(skipString, failString: failString))
  258. // failure(skipString, failString)
  259. // self.appendErrorInfo(skipString, failString: failString)
  260. skipString = NSString()
  261. failString = NSString()
  262. checkString = checkString.substring(from:1) as NSString
  263. resultStr = resultStr.substring(from:1) as NSString
  264. successCount = successCount + 1
  265. callback(NSAttributedString(string: subc as String))
  266. }else if (["\n", "\r", " "].contains(subc)) {
  267. // 两个字符不相同,但 CheckString 首字符 为 空格或回车
  268. callback(NSAttributedString(string: subc as String))
  269. maxSize -= 1;
  270. checkString = checkString.substring(from:1) as NSString
  271. }else if (cRange.location != NSNotFound &&
  272. rRange.location != NSNotFound) {
  273. // 两个字符均出现在另外一个字符 串中
  274. if min(cRange.location, rRange.location) >= 10 {
  275. // let pc = checkString.substring(with: NSMakeRange(0, min(checkString.length, cRange.location)))
  276. // let pr = resultStr.substring(with: NSMakeRange(0, min(resultStr.length, rRange.location)))
  277. // NSLog("C(\(cCount)):%.2f%%:\(pc)", cdegree)
  278. // NSLog("R(\(rCount)):%.2f%%:\(pr)", rdegree)
  279. if (cRange.location > rRange.location*3) {
  280. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  281. failString = failString.appending(subr as String) as NSString
  282. resultStr = resultStr.substring(from:1) as NSString
  283. }else if (cRange.location*3 < rRange.location) {
  284. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  285. skipString = skipString.appending(subc as String) as NSString
  286. checkString = checkString.substring(from:1) as NSString
  287. }else {
  288. let checkSubString = checkString.substring(with: NSMakeRange(0, cRange.location))
  289. let cCount = checkCountIn(checkSubString as NSString, inStr: resultStr);
  290. let rCount = checkCountIn(resultStr.substring(with: NSMakeRange(0, rRange.location)) as NSString, inStr: checkString)
  291. let cdegree = Float(cCount) / Float(cRange.location)
  292. let rdegree = Float(rCount) / Float(rRange.location)
  293. if (cdegree > 0.2) {
  294. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  295. failString = failString.appending(subr as String) as NSString
  296. resultStr = resultStr.substring(from:1) as NSString
  297. }else if (rdegree > 0.2) {
  298. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  299. skipString = skipString.appending(subc as String) as NSString
  300. checkString = checkString.substring(from:1) as NSString
  301. } else if (cdegree > rdegree * 2.0) {
  302. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  303. failString = failString.appending(subr as String) as NSString
  304. resultStr = resultStr.substring(from:1) as NSString
  305. }else if (cdegree * 2.0 < rdegree) {
  306. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  307. skipString = skipString.appending(subc as String) as NSString
  308. checkString = checkString.substring(from:1) as NSString
  309. }else if (cCount < rCount) {
  310. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  311. failString = failString.appending(subr as String) as NSString
  312. resultStr = resultStr.substring(from:1) as NSString
  313. }else {
  314. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  315. skipString = skipString.appending(subc as String) as NSString
  316. checkString = checkString.substring(from:1) as NSString
  317. }
  318. }
  319. }else if min(cRange.location, rRange.location) >= 2 {
  320. // 首部字符在对方字串中位置偏移最小值 大于 2
  321. var scale = (resultStr.length > 0) ? (Float(checkString.length) / Float(resultStr.length)) : Float(1.0)//, Float(1.0))
  322. let nextc = checkString.substring(with: NSRange(location: 1, length: 1)) as NSString
  323. let nextr = resultStr.substring(with: NSRange(location: 1, length: 1)) as NSString
  324. var ncRange = checkString.range(of: nextr as String)
  325. var nrRange = resultStr.range(of: nextc as String)
  326. if nrRange.location == NSNotFound {
  327. nrRange.location = 100000;
  328. }
  329. if ncRange.location == NSNotFound {
  330. ncRange.location = 100000;
  331. }
  332. if (min(nrRange.location, ncRange.location) < min(cRange.location, rRange.location)) {
  333. // 第二位字符,在对方字串中位置偏移最小值小于 首字符偏移
  334. if ncRange.location < Int(Float(nrRange.location) * scale) {
  335. //‘subr' 字符串有在‘checkString’ 偏移 小于'subc'在’checkString‘中 的偏移,优先移除checkString第一位
  336. skipString = skipString.appending(subc as String) as NSString
  337. checkString = checkString.substring(from:1) as NSString
  338. }else {
  339. //‘subr' 字符串有在‘checkString’ 偏移 不小于'subc'在’checkString‘中 的偏移,优先移除resultStr第一位
  340. failString = failString.appending(subr as String) as NSString
  341. resultStr = resultStr.substring(from:1) as NSString
  342. }
  343. }else if (cRange.location < Int(Float(rRange.location) * scale)) {
  344. //‘subr' 字符串有在‘checkString’ 偏移 小于'subc'在’checkString‘中 的偏移,优先移除checkString第一位
  345. skipString = skipString.appending(subc as String) as NSString
  346. checkString = checkString.substring(from:1) as NSString
  347. }else {
  348. //‘subr' 字符串有在‘checkString’ 偏移 不小于'subc'在’checkString‘中 的偏移,优先移除resultStr第一位
  349. failString = failString.appending(subr as String) as NSString
  350. resultStr = resultStr.substring(from:1) as NSString
  351. }
  352. }else {
  353. // var scale = (skipString.length > 0) ? (Float(checkString.length) / Float(skipString.length)) : Float(1.0)
  354. // if (checkString.length > skipString.length && cRange.location <= Int(Float(rRange.location)*scale)) {
  355. // //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  356. // skipString = skipString.appending(subc as String) as NSString
  357. // checkString = checkString.substring(from:1) as NSString
  358. // }else if (checkString.length <= skipString.length && cRange.location > Int(Float(rRange.location)*scale)) {
  359. // failString = failString.appending(subr as String) as NSString
  360. // resultStr = resultStr.substring(from:1) as NSString
  361. // }else
  362. if (cRange.location < rRange.location) {
  363. //‘subr' 字符串有在‘checkString’ 偏移 小于'subc'在’checkString‘中 的偏移,优先移除checkString第一位
  364. skipString = skipString.appending(subc as String) as NSString
  365. checkString = checkString.substring(from:1) as NSString
  366. }else {
  367. //‘subr' 字符串有在‘checkString’ 偏移 不小于'subc'在’checkString‘中 的偏移,优先移除resultStr第一位
  368. failString = failString.appending(subr as String) as NSString
  369. resultStr = resultStr.substring(from:1) as NSString
  370. }
  371. }
  372. }else if (cRange.location != NSNotFound) {
  373. // let checkSubString = checkString.substring(with: cRange)
  374. // if (checkCountIn(checkSubString as NSString, inStr: resultStr) < Int(Float(cRange.location) * 0.6)) {
  375. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  376. skipString = skipString.appending(subc as String) as NSString
  377. checkString = checkString.substring(from:1) as NSString
  378. // }else {
  379. // failString = failString.appending(subr as String) as NSString
  380. // resultStr = resultStr.substring(from:1) as NSString
  381. // }
  382. }else if (rRange.location != NSNotFound) {
  383. // let resultSubString = resultStr.substring(with: rRange)
  384. // if (checkCountIn(resultSubString as NSString, inStr: checkString) < Int(Float(rRange.location) * 0.5)) {
  385. //‘subc' 字符串有在‘resultStr’中,但'subr'不在’checkString‘中,resultStr 往后推一
  386. failString = failString.appending(subr as String) as NSString
  387. resultStr = resultStr.substring(from:1) as NSString
  388. // }else {
  389. // skipString = skipString.appending(subc as String) as NSString
  390. // checkString = checkString.substring(from:1) as NSString
  391. // }
  392. }else {
  393. // 两个子字串均未找到
  394. skipString = skipString.appending(subc as String) as NSString
  395. failString = failString.appending(subr as String) as NSString
  396. checkString = checkString.substring(from:1) as NSString
  397. resultStr = resultStr.substring(from:1) as NSString
  398. }
  399. }
  400. skipString = skipString.appending(checkString as String) as NSString
  401. failString = failString.appending(resultStr as String) as NSString
  402. // failure(skipString, failString)
  403. callback(attributeStringWith(skipString, failString: failString))
  404. callback(NSAttributedString(string: "\n"))
  405. let degree = (maxSize>1) ? Double(Float(successCount)/Float(maxSize) * 100) : 0
  406. return degree
  407. }
  408. }
  409. func checkCountIn(_ subStr:NSString, inStr:NSString) -> Int {
  410. let countInfo = NSMutableArray()
  411. for i in 0...(subStr.length - 3) {
  412. let tStr = subStr.substring(with: NSMakeRange(i, 3))
  413. let range = inStr.range(of: tStr)
  414. if (range.location != NSNotFound) {
  415. countInfo.add(range.location)
  416. }
  417. }
  418. return findLISLength(countInfo as! [Int]);
  419. }
  420. func findLISLength(_ nums: [Int]) -> Int {
  421. let n = nums.count
  422. if n == 0 {
  423. return 0
  424. }
  425. var dp = Array(repeating: 1, count: n)
  426. var maxLen = 1
  427. for i in 1 ..< n {
  428. for j in 0 ..< i {
  429. if nums[i] > nums[j] {
  430. dp[i] = max(dp[i], dp[j] + 1)
  431. }
  432. }
  433. maxLen = max(maxLen, dp[i])
  434. }
  435. return maxLen
  436. }
  437. // Read File
  438. func readTextFile(_ filePath:NSString) -> String? {
  439. if NSArray(array: ["TXT", "txt"]).contains(filePath.pathExtension) {
  440. var checkString = try? NSString.init(contentsOfFile: filePath as String, encoding: NSUTF8StringEncoding)
  441. if (checkString != nil) {
  442. // checkString = checkString!.replacingOccurrences(of: "\n", with: "") as NSString
  443. // checkString = checkString!.replacingOccurrences(of: " ", with: "") as NSString
  444. return checkString! as String
  445. }
  446. return nil
  447. }else if NSArray(array: ["rtf", "RTF"]).contains(filePath.pathExtension) {
  448. // Load check file
  449. let checkData = NSData.init(contentsOfFile: filePath as String) as! Data
  450. var documentAttributes:NSDictionary!
  451. let checkAttString = NSAttributedString.init(rtf: checkData, documentAttributes: &documentAttributes)
  452. var checkString = NSString(string: checkAttString!.string) as NSString
  453. var pureString = checkString.replacingOccurrences(of: "\n", with: "") as NSString
  454. pureString = pureString.replacingOccurrences(of: " ", with: "") as NSString
  455. // 常规 rtf 读取失败
  456. //使用框排进行读取
  457. if (pureString.length > 0) {
  458. return checkString as String?
  459. }
  460. var resultString = try? NSString.init(contentsOfFile: filePath as String, encoding: NSUTF8StringEncoding)
  461. if (nil != resultString && !resultString!.contains("\\shptxt\\shptxt")) {
  462. resultString = resultString!.replacingOccurrences(of: "\n", with: "") as NSString
  463. resultString = resultString!.replacingOccurrences(of: " ", with: "") as NSString
  464. return resultString! as String
  465. }
  466. //识别字符串 \shptxt\shptxt ... }
  467. let pageInfoStrings = resultString!.components(separatedBy: "\\shptxt\\shptxt") as NSArray
  468. var finalString = ""
  469. if pageInfoStrings.count > 0 {
  470. let subStrings = pageInfoStrings.subarray(with: NSMakeRange(1, Int(pageInfoStrings.count - 1))) as! [String]
  471. for pageInfoString in subStrings {
  472. let endRange = NSString(string: pageInfoString).range(of: "}")
  473. finalString = finalString.appending(NSString(string: pageInfoString).substring(to: endRange.location))
  474. }
  475. }
  476. //识别所有 【空格 ~ \】 之间的值,并进行缝合
  477. // Detect all strings between Spaces and \ and stitch
  478. let strings = finalString.components(separatedBy: " ")
  479. var resultStr = "" as NSString
  480. for str in strings {
  481. let markStr = str as NSString
  482. if (markStr.contains("\\f")) {
  483. let fRange = markStr.range(of: "\\f")
  484. let cRange = markStr.range(of: "\\c")
  485. let bRange = markStr.range(of: "\\b")
  486. let iRange = markStr.range(of: "\\i")
  487. let eRange = markStr.range(of: "\\e")
  488. let pRange = markStr.range(of: "\\p")
  489. let minPos = min(Int(fRange.location),
  490. Int(cRange.location),
  491. Int(bRange.location),
  492. Int(iRange.location),
  493. Int(eRange.location),
  494. Int(pRange.location))
  495. resultStr = resultStr.appending(markStr.substring(to: minPos)) as NSString
  496. }else {
  497. resultStr = resultStr.appending(markStr as String) as NSString
  498. }
  499. }
  500. resultStr = self.replaceUnicodeString(resultStr)
  501. resultStr = resultStr.replacingOccurrences(of: "\n", with: "") as NSString
  502. resultStr = resultStr.replacingOccurrences(of: " ", with: "") as NSString
  503. resultStr = resultStr.replacingOccurrences(of: "\\pard", with: "") as NSString
  504. resultStr = resultStr.replacingOccurrences(of: "\\par", with: "") as NSString
  505. return resultStr as String?
  506. }
  507. return nil
  508. }
  509. override func compareFiles() -> NSArray? {
  510. let items = NSMutableArray()
  511. let files = DataModel.shared.originFilesFor(_fileType, type: _type) as [String]
  512. for fileName in files {
  513. let sItems = compareFiles(fileName)
  514. if sItems != nil && sItems!.count != 0 {
  515. items.addObjects(from: sItems as! [Any])
  516. }
  517. }
  518. return items
  519. }
  520. override func compareFiles(_ fileName: String) -> NSArray? {
  521. let files = NSMutableArray()
  522. let checkDirectory = self.checkFileDirectory()
  523. let resultDirectory = self.resultFileDirectory()
  524. let nName = NSString(string: fileName).deletingPathExtension.appending(".\(self.extention())")
  525. let rComparePath = NSString(string: resultDirectory).appendingPathComponent(nName)
  526. let cComparePath = NSString(string: checkDirectory).appendingPathComponent(nName)
  527. if (FileManager.default.fileExists(atPath: rComparePath) &&
  528. FileManager.default.fileExists(atPath: rComparePath+".rtf")) {
  529. let fileInfo = NSMutableDictionary.fileInfoWith(fileName,
  530. refFilePath: nil,
  531. resultPath: rComparePath,
  532. comparePath: cComparePath,
  533. objc: self)
  534. files.add(fileInfo)
  535. }
  536. return files
  537. }
  538. /**
  539. Replace the refrence image for next image check test
  540. */
  541. override func canUpdateRefImage() -> Bool {
  542. return false
  543. }
  544. override func updateRefImage() {
  545. }
  546. override func canUpdateRefImage(_ fileName:String) -> Bool {
  547. return false
  548. }
  549. override func updateRefImage(_ fileName:String) {
  550. }
  551. }