代码改变世界

大数计算,OC代码

2014-07-11 22:42  long桃子  阅读(227)  评论(0)    收藏  举报
  1 #pragma mark - 说明
  2 #if 0
  3     1、传入字符串表示的整数只能是正整数。
  4     2、不能带有除了阿拉伯小写数字以外的任何字符。
  5     3、目前只完成了大数的加减和乘法。除法有待解决。
  6     现在传递进来的参数字符串,不能是带有标点符号或者加减乘除其他符号的字符串。否则计算功能失效。另外减法在leftNum<rightNum的时候,得到返回值结果带有一个‘-’负号,不能将他在读进行本函数中的进一步计算,必须进过处理。
  7     对于上面这一点不足,有待改进。算法和代码优化待改进。
  8 #endif
  9 #pragma mark -
 10 
 11 
 12 #import <Foundation/Foundation.h>
 13 
 14 @interface BigNumMath : NSObject
 15 
 16 /*两个数相加,返回结果的字符串*/
 17 -(NSString *)bnm:(NSString *)leftNum Add:(NSString *)rightNum;
 18 
 19 /*两个数相减,返回结果的字符串*/
 20 -(NSString *)bnm:(NSString *)leftNum Minus:(NSString *)rightNum;
 21 
 22 /*  比较两个字符串表示整数的大小,前者大返回:NSOrderedDescending
 23     后者大返回:NSOrderedAscending大小相同放回:NSOrderedSame    */
 24 -(NSComparisonResult)bnm:(NSString *)leftNum LargerThan:(NSString *)rightNum;
 25 
 26 /*两个数相乘,返回结果的字符串*/
 27 -(NSString *)bnm:(NSString *)leftNum Multiply:(NSString *)rightNum;
 28 
 29 /*一个整形数据int 与一个大数乘积,放回结果NSString*/
 30 -(NSString *)getStringWithInt:(int)num Multiply:(NSString *)rightNum;
 31 
 32 @end
 33 //==================方法实现部分:
 34 #import "BigNumMath.h"
 35 
 36 #pragma mark - Catogary
 37 @interface NSString (NSStringMethod)
 38 +(NSArray *)getCharArrayFromNSString:(NSString *)charsString;
 39 @end
 40 @implementation NSString (NSStringMethod)
 41 
 42 +(NSArray *)getCharArrayFromNSString:(NSString *)charsString
 43 {
 44     NSMutableArray *charArray = [[NSMutableArray alloc] initWithCapacity:0];
 45     int index = 0;
 46     while (1) {
 47         NSString *charOne = [charsString substringWithRange:NSMakeRange(index, 1)];
 48         [charArray addObject:charOne];
 49         index++;
 50         if (index>=[charsString rangeOfString:charsString].length) {
 51             break;
 52         }
 53     }
 54     return charArray;
 55 }
 56 
 57 @end
 58 
 59 #pragma mark - BNM_Class
 60 @implementation BigNumMath
 61 {
 62     NSMutableArray *leftArray;
 63     NSMutableArray *rightArray;
 64     NSMutableArray *destArray;
 65     
 66     char *left;
 67     char *right;
 68 }
 69 
 70 -(id)init{
 71     if (self=[super init]) {
 72         
 73     }
 74     return self;
 75 }
 76 
 77 #pragma mark - MultiplyWithInt
 78 -(NSString *)getStringWithInt:(int)num Multiply:(NSString *)rightNum
 79 {
 80     NSMutableArray *rArr = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:rightNum]];
 81 //    printf("\n n = %d, rArr = %s \n",num,[[rArr componentsJoinedByString:@""] UTF8String]);
 82     
 83     NSMutableArray *destArr = [NSMutableArray arrayWithCapacity:0];
 84     int car1 = 0;
 85     int temp = 0;
 86     int location = rArr.count-1;
 87     while (1)
 88     {
 89         temp = [[rArr objectAtIndex:location] intValue]*num+car1;
 90         car1 = temp/10;
 91         [destArr insertObject:[NSString stringWithFormat:@"%d",temp%10] atIndex:0];
 92         if (location==0) {
 93             if (car1!=0) {
 94                 [destArr insertObject:[NSString stringWithFormat:@"%d",car1] atIndex:0];
 95             }
 96             break;
 97         }else{
 98             location--;
 99         }
100     }
101     NSString *numD = [destArr componentsJoinedByString:@""];
102 
103     return numD;
104 }
105 
106 #pragma mark - MultiplyMethod
107 -(NSString *)bnm:(NSString *)leftNum Multiply:(NSString *)rightNum
108 {
109     NSArray *lArr = [NSString getCharArrayFromNSString:leftNum];
110     NSArray *rArr = [NSString getCharArrayFromNSString:rightNum];
111     
112     /*得到有效数位的数组*/
113     NSArray *elArray = [self getEffectiveArrayFromArray:lArr];
114     NSArray *erArray = [self getEffectiveArrayFromArray:rArr];
115     
116     //查找有效位数
117     int LenOfL = elArray.count;
118     int LenOfR = erArray.count;
119     
120     
121     NSMutableArray *elemArr = [NSMutableArray arrayWithCapacity:0];
122     for (int i=1; i<=LenOfL; i++) {
123         NSMutableString *numLayer = (NSMutableString *)[self getStringWithInt:[[elArray objectAtIndex:LenOfL-i] intValue] Multiply:rightNum];
124         for (int j=1; j<i; j++) {
125             [numLayer appendString:@"0"];
126         }//加法运算对齐处理
127         [elemArr addObject:numLayer];
128     }
129     
130     NSMutableString *numD = [NSMutableString stringWithString:@"0"];
131     for (int l=0; l<LenOfL; l++) {
132         numD = (NSMutableString *)[self bnm:numD Add:[elemArr objectAtIndex:l]];
133     }
134     
135     return numD;
136 }
137 
138 #pragma mark - AddMethod
139 -(NSString *)bnm:(NSString *)leftNum Add:(NSString *)rightNum
140 {
141 //    printf("left = %s,%c right = %s\n",[leftNum UTF8String],9,[rightNum UTF8String]);
142 
143     leftArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:leftNum]];
144     
145     rightArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:rightNum]];
146     
147     destArray = [[NSMutableArray alloc] initWithCapacity:0];
148     
149 
150     NSMutableArray *shortArray = leftArray.count<rightArray.count ? leftArray:rightArray;
151     NSMutableArray *longArray = leftArray.count<rightArray.count ? rightArray:leftArray;
152     
153     int LenOfL = leftArray.count;
154     int LenOfR = rightArray.count;
155     int LenOfMax = MAX(LenOfL, LenOfR);
156     int LenOfMin = MIN(LenOfL, LenOfR);
157     for (int i=0; i<LenOfMax-LenOfMin; i++) {
158         [shortArray insertObject:@"0" atIndex:0];
159     }//这里先使得leftArray为短数组
160 
161     int carray = 0;
162     int location = rightArray.count-1;
163     while (1)
164     {
165         int temp = [[shortArray objectAtIndex:location] intValue] + [[longArray objectAtIndex:location] intValue]+carray;
166         [destArray insertObject:[NSString stringWithFormat:@"%d",temp%10] atIndex:0];
167         carray = temp/10;
168         
169         
170         if (location==0) {
171             if (carray!=0) {
172                 [destArray insertObject:[NSString stringWithFormat:@"%d",carray] atIndex:0];
173             }
174             break;
175         }else{
176             location--;
177         }
178     }
179     
180     NSString *sumD = [destArray componentsJoinedByString:@""];
181     
182     return sumD;
183 }
184 
185 #pragma mark - MinusMethod
186 -(NSString *)bnm:(NSString *)leftNum Minus:(NSString *)rightNum
187 {
188 //    printf("left = %s,%c right = %s\n",[leftNum UTF8String],9,[rightNum UTF8String]);
189 //
190 //    
191 //    printf("arrLeft = %s,arrRight = %s\n",[[leftArray componentsJoinedByString:@""] UTF8String],[[rightArray componentsJoinedByString:@""] UTF8String]);
192     
193     destArray = [[NSMutableArray alloc] initWithCapacity:0];
194     
195     NSComparisonResult result = [self bnm:leftNum LargerThan:rightNum];
196     if (result==NSOrderedSame) {
197         return [NSString stringWithFormat:@"0"];
198     }else if (result==NSOrderedDescending){
199         leftArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:leftNum]];
200         rightArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:rightNum]];
201     }else if(result ==NSOrderedAscending){
202         leftArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:rightNum]];
203         rightArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:leftNum]];
204     }//确保leftArray > rightArray
205     
206     
207 //    NSMutableArray *shortArray = leftArray.count<rightArray.count ? leftArray:rightArray;
208 //    NSMutableArray *longArray = leftArray.count<rightArray.count ? rightArray:leftArray;
209     
210     int LenOfL = leftArray.count;
211     int LenOfR = rightArray.count;
212     int LenOfMax = MAX(LenOfL, LenOfR);
213     int LenOfMin = MIN(LenOfL, LenOfR);
214     for (int i=0; i<LenOfMax-LenOfMin; i++) {
215         [rightArray insertObject:@"0" atIndex:0];
216     }//这里先使得leftArray为短数组
217     
218 //    printf("shortArray = %s,longArray = %s\n",[[shortArray componentsJoinedByString:@""] UTF8String],[[longArray componentsJoinedByString:@""] UTF8String]);
219 //    
220 //    
221 //    printf("lenOFL = %d,  LenOfR = %d, LenOfMax = %d\n",LenOfL,LenOfR,LenOfMax);
222     
223     int carray = 0;
224     int lend = 0;
225     int location = rightArray.count-1;
226     while (1)
227     {
228         if ([[leftArray objectAtIndex:location] intValue]<[[rightArray objectAtIndex:location] intValue]) {
229             lend = 10;
230             carray = 1;
231             [leftArray replaceObjectAtIndex:location-1 withObject:[NSString stringWithFormat:@"%d",[[leftArray objectAtIndex:location-1] intValue]-carray]];
232         }
233         int temp = [[leftArray objectAtIndex:location] intValue] +lend - [[rightArray objectAtIndex:location] intValue];
234         [destArray insertObject:[NSString stringWithFormat:@"%d",temp] atIndex:0];
235         
236         if (location==0) {
237             break;
238         }else{
239             lend = 0;
240             carray = 0;
241             location --;
242         }
243         
244     }
245     if (result==NSOrderedDescending) {
246         NSString *sumD = [destArray componentsJoinedByString:@""];
247         return sumD;
248     }
249     
250     NSMutableString *sumD = [NSMutableString stringWithFormat:@"-%@",[destArray componentsJoinedByString:@""]];
251     
252     return sumD;
253 }
254 #pragma mark - NSCompareResult
255 -(NSComparisonResult)bnm:(NSString *)leftNum LargerThan:(NSString *)rightNum
256 {
257     printf("left = %s,%c right = %s\n",[leftNum UTF8String],9,[rightNum UTF8String]);
258 
259     leftArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:leftNum]];
260     
261     rightArray = [NSMutableArray arrayWithArray:[NSString getCharArrayFromNSString:rightNum]];
262     
263     //查找有效位数
264     int LenOfL = [self getEffectiveNumFromArray:leftArray];
265     int LenOfR = [self getEffectiveNumFromArray:rightArray];
266     int rddL = leftArray.count - LenOfL;
267     int rddR = rightArray.count - LenOfR;
268    
269 
270     if (LenOfL > LenOfR) {
271         return NSOrderedDescending;
272     }else if (LenOfL < LenOfR){
273         return NSOrderedAscending;
274     }
275     
276    /*去除无效数位,保留有效数位*/
277     for (int i=0; i<rddL; i++){
278         [leftArray removeObjectAtIndex:0];
279     }
280     for (int j=0; j<rddR; j++){
281         [rightArray removeObjectAtIndex:0];
282     }
283     
284     for (int i=0; i<LenOfR; i++) {
285         int nsl = [[leftArray objectAtIndex:i] intValue];
286         int nsr = [[rightArray objectAtIndex:i] intValue];
287         if (nsl > nsr ) {
288             return NSOrderedDescending;
289         }else if (nsl < nsr ){
290             return NSOrderedAscending;
291         }else{
292             continue;
293         }
294     }
295     return NSOrderedSame;
296 }
297 #pragma mark - 查找有效数位数(0000123,有效位为3;010023有效位数为5)
298 -(int)getEffectiveNumFromArray:(NSArray *)sArray
299 {
300     int mark = 0;
301     int ecount = 0;
302     for (NSString *ns in sArray) {
303         if ([ns intValue]==0) {
304             mark++;
305         }else
306             break;
307     }
308     ecount = sArray.count-mark;
309     return ecount;
310 }
311 
312 #pragma mark - 将数组保留有效位数(00012030,-->12030)
313 -(NSArray *)getEffectiveArrayFromArray:(NSArray *)sArray
314 {
315     NSMutableArray *mArray = [NSMutableArray arrayWithArray:sArray];
316     int mark = 0;
317     int ecount = 0;
318     for (NSString *ns in sArray) {
319         if ([ns intValue]==0) {
320             mark++;
321             [mArray removeObjectAtIndex:0];
322         }else
323             break;
324     }
325     ecount = sArray.count-mark;
326     return mArray;
327 }
328 
329 #pragma mark - 数组倒置
330 -(NSArray *)getReverseArrayFromArray:(NSArray *)sArray
331 {
332     NSMutableArray *dArray = [NSMutableArray arrayWithArray:sArray];
333     int count = dArray.count;
334     for (int i=0; i<sArray.count/2; i++) {
335         [dArray exchangeObjectAtIndex:i withObjectAtIndex:(count-1-i)];
336     }
337     return dArray;
338 }
339 
340 @end