Nhập xâu thập lục phân nén xâu bằng cách xóa ký tự trống và đổi xâu ra số thập phân……….3 2.. Hãy nhập xâu ký tự số thập lục phân st[] có lẫn các ký tự trống, hãy nén xâu bằng cách xóa hế
Trang 1MỤC LỤC
MỤC LỤC 1
GIỚI THIỆU ĐỀ TÀI……… 2
I Viết một chương trình C để xử lí các công việc sau đây: 2
II Viết chương trình ASM ……… 2
NỘI DUNG BÁO CÁO:……… 3
A Phần C……… 3
I Mô tả các hàm trong chương trình……… 3
II Xây dựng thuật toán……….3
1 Nhập xâu thập lục phân nén xâu bằng cách xóa ký tự trống và đổi xâu ra số thập phân……….3
2 Tính sin(x),cos(x),pi dùng đệ quy………5
3 Tính tổng……… 5
4 Chuyển mã……… 6
III Chương trình và hình minh họa……… 8
B Phần ASM 14 I Mô tả các hàm trong chương trình……… 14
II Xây dựng thuật toán……….14
III Chương trình và hình minh họa 15
Trang 2GIỚI THIỆU ĐỀ TÀI
I Viết một chương trình C để xử lí các công việc sau đây:
1 Hãy nhập xâu ký tự số thập lục phân st[] có lẫn các ký tự trống, hãy nén xâu bằng cách xóa hết các ký tự trống, rồi đổi xâu st[] ra số thập phân tương ứng vd: char st[]=” 1 8 F
”; =>char st[]=”18F”;=>unsigned int n=399.
2 Viết các hàm đệ quy tsin(), tcos(), tpi() để tính các dãy số biểu diển hàm chuẩn
sin(x), cos(x) và hằng chuẩn M_PI, với x=0.25 và độ chính xác ef=1e-5
3 Hãy gán tx=(int)(n+tsin()*tpi())/tcos());viết hàm doihe() để đổi tx ra số nhị phân, sau
đó đổi từ số nhị phân ra số thập lục phân, rồi đổi từ số thập lục phân ra lại số thập phân vd: tx=140=>10001100=>0x8C=> 140
II Viết chương trình ASM :
Xử lý xâu ký tự số thập phân: thủ tục DOC_XAU để nhập các ký tự thâp phân
vào xâu tphan db 5 dup(0) , Hãy đổi xâu tphan ra số thập phân, tương ứng, rôi đổi số thập phân ra xâu số thập lục phân (tlp db 4 dup(0).
Trang 3NỘI DUNG BÁO CÁO:
A Phần C
I Mô tả các hàm trong chương trình
-strstr(chuoi,” ”);//trả lại vị trí tìm thấy của ký tự trống trong chuỗi
-strim(chuoi);//tìm và xóa ký tự trống trong chuỗi
-strlen(chuoi);//tính độ dài chuỗi
-memmove(p,p+1,strlen(chuoi)-(p-chuoi));//dich chuỗi sang phải 1 đơn vị
-tpi(exp,i);//tính pi
-tsin(x,i,exp);//tính sin
-tcos(x,i,exp);//tính cos
-gt(n);//tính giai thừa n
-lt(x,y);//tính x^y
-tong(n,i,exp,x);//tính tổng
-nph(x);//đổi số thập phân sang nhị phân
-tlph(t);//đổi số nhị phân sang thập lục phân
-tp(k);//đổi từ số thập lục phân sang nhị phân
-tp_np_tlph_tp(a);//xuất từ thập phân-nhị phân-thập lục phân-thập phân
II Xây dựng thuật toán:
1 Nhập xâu thập lục phân,nén xâu bằng cách xóa ký tự trống,sau đó chuyển sang số thập phân:
a Nhập xâu thập phân: chứa các ký tự 0,1,2,3,4,5,6,7,8,9,a,b,c,d,e,f,A,B,C,D,E,F -Bước 1: Khai báo con trỏ p-trỏ vào chuỗi
-Bước 2: dùng vòng lặp while để kiểm tra ký tự trống
-p=strstr(chuoi,” ”);//trả lại vị trí tìm thấy của ký tự trống trong chuỗi
-memmove(p,p+1,strlen(chuoi)+(chuoi-p);//khi đó ta sẽ xét chuỗi từ vị trí
khoảng trắng"_"và xóa khoảng đó,và dich chuỗi qua phải 1 dơn vị
-Bước 3: so sánh (chuoi[0]==’’) dịch chuỗi qua phải 1 dơn vị,độ dài chuỗi giảm xuống
1
-Bước 4: so sánh (chuoi[strlen(chuoi)-1]==’’),xét hết chuỗi ,nếu chưa hết ta quay lại
bước 2
chuoi[strlen(chuoi)-1]=0;// thêm số 0 vào cuối chuỗi
Trang 4char *trim(char *chuoi)
{
char *p;
while (p=strstr(chuoi," "))
memmove(p,p+1,strlen(chuoi)-(p-chuoi));
if (chuoi[0]==' ')
memmove(chuoi,chuoi+1,strlen(chuoi)-1);
if (chuoi[strlen(chuoi)-1]==' ')
chuoi[strlen(chuoi)-1]=0;
return chuoi;
}
b -Tạo hàm luythua() để đổi từ xâu thập luc phân số thập phân
Code:
int lt(int x, int y)
{
int i,t=1;
for(i=1;i<=y;i++)
t=t*x;
return t;
}
c Tạo hàm in xâu thập lục phân được chuyển sang số thập phân:
Thuật toán:
-Bước 1: gọi hàm nhập xâu thập lục phân: st=trim();
Biến s chứa độ dài xâu cần chuyển s=strlen();
-Bước 2: cho i=0;j=s-1;
-Bước 3:- Nếu (st[i]>=’0’)&&(st[i]<=’9’) h=st[i]-48đổi sang số thập phân
(h>=0)&&(h<=9)
- Nếu (st[i]>=’a’)&&(st[i]<f) h=st[i]-87 đổi ký tự thường sang số thập phân (h>=10)&&(h<=15)
-Nếu (st[i]>=’A’&&st[i]<=’F’) h=st[i]-55 đổi ký tự in sang số thập phân -Gán :so= so+h*lt(16,j );tính tổng dãy số
-Bước 4: So sánh i với s: nếu(i==s) trả về giá trị của so.kết thúc
Ngược lại: i=i+1; quay lại bước 3
-Code:
int xau_int(char st[20])
{
char h;
int i,j,s=0,so=0;
st=trim(st);
s=strlen(st);
j=s-1;
for(i=0;i<s;i++)
{
if((st[i]>='0')&&(st[i]<='9')) h=st[i]-48;
else if ((st[i]>='a')&&(st[i]<='f')) h=st[i]-87;
else if((st[i]>='A')&&(st[i]<='F')) h=st[i]-55;
else ;
so=so+h*lt(16,j );
}
return so;
}
Trang 52).Tính sin(x),cos(x),pi dùng đệ quy:
a) Tính số pi:
Thuật toán:
-Bước 1: khai báo biến s:kiểu float chứa tổng pi
-Bước 2: cho i=0;
Gán s=((-1)^i)*4/(2*i+1);
-Bước 3: +So sánh s với hằng số epsilon: nếu (s<=epsilon) return s; kết thúc
+Ngược lại :gọi đệ quy trả về s=s+tpi(exp,i+1);
-Chương trình:
Code:
float tpi(float exp,int i)
{
float s;
s=(pow(-1,i)*4/(2*i+1));
if ( fabs(s)<=exp) return s;
else return (s+tpi(exp,i+1));
}
b) Tính sin(x):
Thuật toán:
-Bước 1: cho i=0;
gán s=((-1)^i)*(x,2*i+1)/(gt(2*i+1));
-Bước 2: so sánh s và epsilon:
+Nếu (s<=epsilon) trả về giá trị s.kết thúc
+Ngược lại gọi đệ quy (s+tsin(x,i+1,exp));
-Code:
float tsin(float x,int i,float exp)
{
float s;
s=(pow(-1,i)*pow(x,2*i+1))/(gt(2*i+1));
if (fabs(s)<=exp) return s;
else return (s+tsin(x,i+1,exp));
}
c) Tính cos(x):
Thuật toán:
-Bước 1: cho i=0;
gán s=((-1)^i)*(x,2*i+)/(gt(2*i+1));
-Bước 2: so sánh s và epsilon:
+Nếu (s<=epsilon) trả về giá trị s.kết thúc
+Ngược lại gọi đệ quy (s=s+tcos(x,i+1,exp));
Code:
float tcos(float x,int i,float exp)
{
float s;
s=(pow(-1,i)*pow(x,2*i))/(gt(2*i));
if (fabs(s)<=exp) return s;
else return (s+tcos(x,i+1,exp));
}
Trang 63) Tính tổng:tx=int(n+tsin()*tpi()/tcos());
Thuật toán:
-Bước 1:gán a=tsin();b=tcos();c=tpi();
-Bước 2:gán s=a*c/b;
-Bước 3:lấy phần nguyên của s: nếu float s=30.123;int s=30;
-Bước 4:trả về giá trị tổng: tong(n,i,exp,x)=s+n; kết thúc
Code:
int tong(int n,int i,float exp,float x)
{
float a=tsin(x,i,exp);
float b=tcos(x,i,exp);
float c=tpi(exp,i);
float s=a*c/b;
int s1=s;
return s1+n;
}
4) Chuyển mã: thập phân-nhị phân-thập lục phân-thập phân
-Khai báo: xâu ký tự kiểu char mnph[20]; char mtph[5];
-khai báo biếm dem:đếm số ký tự có trong xâu
-Tạo hàm lũy thừa:lt() để tính giá trị của xâu nhị phân:
-Code:
int lt(char x, char y)
{
char i,t=1;
for (i=1;i<=y;i++)
t=t*x;
return t;
}
a) Hàm đổi từ số thập phân sang nhi phân:
Thuật toán:
-Bước 1: i=0; gán x=a //biến x chứa giá trị của số thập phân cần chuyển
-Bước 2: so sánh x và 2
-Bước 2.1:(nếu x<2) return i; kết thúc
+Ngược lại: mnph[i++]=x%2;
x=x/2; quay lại bước 2
Code:
char nph(int a)
{
int x=a,i=0;
while(x>2)
{
mnph[i++]=x%2;
x=x/2;
}
return i;
}
Trang 7b) Hàm chuyển từ số nhị phân sang thập lục phân:
Thuật toán:
-từ xâu nhị phân chuyển sang thập lục phân: ta có tổ hợp 4 bít nhị phân tạo thành 1 số thập lục phân tương ứng
-Bước 1:j=0; gán i=0;//đếm số ký tự xâu nhị phân
-Bước 2:gán x=x+mnph[i]*lt(2,j++);
Nếu:((i+1)%4==0)//4 bít là một số thập lục phân
Nếu:( (0<=x)&&(x<=9) )x=x+48//in ra số thập lục phân
Nếu:( (10<=x)&&(x<=15)) x=x+55//in ra dạng ký tự
-Bước 3: so sánh: nếu i bằng độ dài xâu nhi phân (i==t) trả về giá trị x;kết thúc
Ngược lại : i++ quay lại bước 2
Code:
char tlp(char t)
{
int i,j=0,x=0;
char k=0;
for(i=0;i<t;i++)
{
x=x+mnph[i]*lt(2,j++);
if(((i+1)%4==0)||(i==t-1))
{
if((x>=0)&&(x<=9)) x=x+48;
if((x>=10)&&(x<=15)) x=x+55;
mtlp[k++]=x;
x=0;
j=0;
}
}
return k;
}
c) Hàm chuyển từ thập lục phân sang thập phân:
Thuật toán:
-Bước 1:gán j=0;i=0; //đếm số chữ số được chuyển
-Bước 2: x=mtlp[i];
Nếu:( (x>=48)&&(x<=57)) x=x-48;chuyển từ thập luc phân sang số thập phân
Nếu :((x>=65&&x<=70)) x=x-55;chuyển từ dạng ký tự hex sang thập phân
t=t+x*lt(16,j++);đổi từ hexa sang thập phân bằng cách nhân số đó với (16^j) (số
đó nằm ở vị trí thứ j trong dãy)
-Bước 3:so sánh: i và k-tổng số trong dãy
Nếu (i==k) trả về giá trị của số thập phân return t;//kết thúc
Ngược lại: i=i+1 //quay lại bước 2
Trang 8int tp(char k)
{
int i,x,t;
char j=0;
for(i=0;i<k;i++)
{
x=mtlp[i];
if((x>=48)&&(x<57)) x=x-48;
if((x>=65)&&(x<=70)) x=x-55;
t=t+x*lt(16,j++);
}
return t;
}
d) Xuất : Thập phân-nhị phân-thập lục phân-thập phân
Code:
void tp_np_tlp_tp (int a)
{
char i,dem1,dem2;
int t;
printf("%d -> ",a);
dem1 = nph(a);
dem2 = tlp(dem1);
t = tp(dem2);
for(i=dem1-1;i>=0;i ) printf("%d",mnph[i]);
printf(" -> ");
printf("Ox");
for(i=dem2-1;i>=0;i ) printf("%c",mtlp[i]);
printf(" -> %d",t);
}
III.Chương trình và hình minh họa:
1) Nhập xâu thập lục phân nén xâu bằng cách xóa ký tự trống và đổi xâu ra số thập phân:
a) Code:
#include<math.h>
#include<conio.h>
#include<stdio.h>
#include<string.h>
char xau[20];
//=============================
char *trim(char *chuoi);
int lt(int x, int y);
int xau_int(char st[20]);
main()
{
printf("\n\n\n nhap ao xau thap phan: ");
Trang 9scanf("%[ 0123456789abcdefABCDEF]",xau);
printf("\n\n\n So tp la: %d",xau_int(xau));
getch();
}
//=============================
//tim ky tu trong va xoa
char *trim(char *chuoi)
{
char *p;
while (p=strstr(chuoi," "))
memmove(p,p+1,strlen(chuoi)-(p-chuoi));
if (chuoi[0]==' ')
memmove(chuoi,chuoi+1,strlen(chuoi)-1);
if (chuoi[strlen(chuoi)-1]==' ')
chuoi[strlen(chuoi)-1]=0;
return chuoi;
}
//==============================
// Tinh luy thua
int lt(int x, int y)
{
int i,t=1;
for(i=1;i<=y;i++)
t=t*x;
return t;
}
//===============================
// in xau o dang thap phan
int xau_int(char st[20])
{
char h;
int i,j,s=0,so=0;
st=trim(st);
s=strlen(st);
j=s-1;
for(i=0;i<s;i++)
{
if((st[i]>='0')&&(st[i]<='9')) h=st[i]-48;
else if ((st[i]>='a')&&(st[i]<='f')) h=st[i]-87;
else if((st[i]>='A')&&(st[i]<='F')) h=st[i]-55;
else ;
so=so+h*lt(16,j );
}
return so;
}
Trang 10b) Hình minh họa:
2) Viết các hàm đệ quy tsin(), tcos(), tpi() để tính các dãy số biểu diển hàm chuẩn
sin(x), cos(x) và hằng chuẩn M_PI, với x=0.25 và độ chính xác ef=1e-5
3) Gán tx=(int)(n+tsin()*tpi())/tcos());viết hàm doihe() để đổi tx ra số nhị phân, sau đó
đổi từ số nhị phân ra số thập lục phân, rồi đổi từ số thập lục phân ra lại số thập phân
a) Code:
#include<stdio.h>
#include<conio.h>
#include<math.h>
char mnph[20],mtlp[5];
//====================================
//Tinh pi
float tpi(float exp,int i)
{
float s;
s=(pow(-1,i)*4/(2*i+1));
if ( fabs(s)<=exp) return s;
else return (s+tpi(exp,i+1));
}
//====================================
// Tinh giai thua
int gt(int n)
{
if (n==0) return 1;
else return gt(n-1)*n;
}
//====================================
//ham tinh sin(x)
float tsin(float x,int i,float exp)
{
float s;
s=(pow(-1,i)*pow(x,2*i+1))/(gt(2*i+1));
if (fabs(s)<=exp) return s;
else return (s+tsin(x,i+1,exp));
}
Trang 11// ham tinh cos(x)
float tcos(float x,int i,float exp)
{
float s;
s=(pow(-1,i)*pow(x,2*i))/(gt(2*i));
if (fabs(s)<=exp) return s;
else return (s+tcos(x,i+1,exp));
}
//====================================
// ham tinh tong
int tong(int n,int i,float exp,float x)
{
float a=tsin(x,i,exp);
float b=tcos(x,i,exp);
float c=tpi(exp,i);
float s=a*c/b;
int s1=s;
//printf("\n\n tong:%2.3d",s1+n);
return s1+n;
}
//====================================
// ham tinh luy thua
int lt(char x, char y)
{
char i,t=1;
for (i=1;i<=y;i++)
t=t*x;
return t;
}
//====================================
// Chuyen tu thap phan sang nhi phan
char nph(int a)
{
int x=a,i=0;
while(x>0)
{
mnph[i++]=x%2;
x=x/2;
}
return i;
}
//====================================
// Chuyen tu ni phan sang thap luc phan
char tlp(char t)
{
int i,j=0,x=0;
char k=0;
for(i=0;i<t;i++)
{
Trang 12{
if((x>=0)&&(x<=9)) x=x+48;
if((x>=10)&&(x<=15)) x=x+55;
mtlp[k++]=x;
x=0;
j=0;
}
}
return k;
}
//====================================
// Chuyen tu thap luc phan sang thap phan
int tp(char k)
{
int i,x,t;
char j=0;
for(i=0;i<k;i++)
{
x=mtlp[i];
if((x>=48)&&(x<57)) x=x-48;
if((x>=65)&&(x<=70)) x=x-55;
t=t+x*lt(16,j++);
}
return t;
}
//====================================
// In tu thap phan->nhi phan->thap luc phan->thap phan
void tp_np_tlp_tp (int a)
{
char i,dem1,dem2;
int t;
printf("\n Chuyen ma:");
printf("%d -> ",a);
dem1 = nph(a);
dem2 = tlp(dem1);
t = tp(dem2);
for(i=dem1-1;i>=0;i ) printf("%d",mnph[i]);
printf(" -> ");
printf("Ox");
for(i=dem2-1;i>=0;i ) printf("%c",mtlp[i]);
printf(" -> %d",t);
}
//====================================
// chuong trinh chinh
main()
{
float x,exp;
int n,i=0;
printf("\n nhap vao x(radian):");
scanf("%f",&x);
//x=x*3.14/180;
Trang 13printf("\n nhap hang so epsilon:exp=");
scanf("%f",&exp);
printf("\n Nhap n=");
scanf("%d",&n);
printf("\n\n sin(x)=%2.5f",tsin(x,i,exp));
printf("\n\n cos(x)=%2.5f",tcos(x,i,exp));
printf("\n\n pi=%2.5f",tpi(exp,i));
printf("\n\n Tong:%2d",tong(n,i,exp,x));
printf("\n\n");
int a= tong(n,i,exp,x);
tp_np_tlp_tp (a);
getch();
}
b)Hình minh họa:
Trang 14B Phần ASM
I Chức năng của các hàm của ngắt 21h:
– 01h: đợi đọc 1 ký tự từ bàn phím có hiển thị trên màn hình
– 02h: hiển thị 1 ký tự tại vị trí con trỏ trên màn hình
– 09h: xuất 1 chuỗi ký tự lên màn hình
– 0ah: đợi đọc 1 chuỗi ký tự từ bàn phím, kết thúc bằng Enter
– 4ch: kết thúc chương trình và trở về DOS
II Xây dựng thuật toán:
1 Ý tưởng:
- Nhập xâu ký tự số thập phân: thủ tục DOC_XAU để nhập các ký tự thâp phân
vào xâu tphan db 5 dup(0) :dùng chức năng của ngắt 21h hàm 01h cho nhập dữ
liệu và 09h kết xuất
- Sau đó đổi sau tphan sang số thập phân tương ứng bằng cách nhân so10
- Đổi số thập phân ra xâu số thập lục phân và lưu vào xâu tlp db 4 dup(0)
2 Thuật toán:
- Bước 1: nhập xâu số thập phân:
- dùng chức năng 01h của ngắt 21h để nhập số phần tử của xâu:sopt
- dùngthủ tục DOC_XAU để nhập các ký tự thâp phân vào xâu tphan db 5
dup(0).
- gán so=0; và mov al,so; đếm số đã nhập
- Lưu số đã nhập vào vào ô nhớ có địa chỉ ds:bx mov byte ptr [bx],al
- Mổi lần lưu tăng giá trị ô nhở lên 1: inc bx ;tiến hành lặp
- Bước 2: in xâu đã nhập:
- bước lặp: mov dl,byte ptr xtp[bx] ;đọc nội dung ô nhớ tại ds:bx
; thao tác đọc, toán hạng bên trái là thanh ghi dl -dùng chức năng 02h của ngắt 21h để in
-tăng giả trị ô nhớ lên 1: inc bx; và tiến hành lặp
- Bước 3: Đổi xâu thập phân ra số thập phân
- bước lặp: mov al,byte ptr xtp[bx];al đọc nội dung ô nhớ bx
-and al,0fh ; giữ giá trị của al
- xchg ax,dx ;tiến hành đổi chổ ax và dx
- mul so10 ;dxdx*10
- add dx,ax ; dxdx+ax
- inc bx ;tăng địa chỉ ô nhớ lên 1 và tiến hành lặp
- mov ax,dx ; axdx chứa tổng thập phân
- call in10 ;gọi chức năng in10 để tiến hành in giá trị của ax