Перевести код из C++ в чистый Си - C (СИ)

  1. Из-за наличия специфики плюсов (векторы, классы, operator) вообще не удаётся интерпретировать логику, заложенную в код. Помогите, пожалуйста, разобраться и получить хотя бы шаблонный вариант на Си, который я смогу дописать до рабочего. Приведённая программа позволяет интерполировать графики кривыми Безье. В отличие от других сотен вариаций на данную тему не даёт ложных экстремумов. Вот статья на хабре с подробным описанием и примерами. Код программы на гитхабе.C++1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 // TBezierInterpolation.cpp #include <vector> #include <iostream> #include <cmath>   using namespace std;   #define EPSILON 1.0e-5 #define RESOLUTION 32   class Point2D { public:     double x, y;         Point2D() { x = y = 0.0; };     Point2D(double _x, double _y) { x = _x; y = _y; };         Point2D operator +(const Point2D &point) const { return Point2D(x + point.x, y + point.y); };     Point2D operator -(const Point2D &point) const { return Point2D(x - point.x, y - point.y); };     Point2D operator *(double v) const { return Point2D(x * v, y * v); };     void operator +=(const Point2D &point) { x += point.x; y += point.y; };     void operator -=(const Point2D &point) { x -= point.x; y -= point.y; };         void normalize()     {         double l = sqrt(x * x + y * y);         x /= l;         y /= l;     } };   class Segment { public:     Point2D points[4];         void calc(double t, Point2D &p)     {         double t2 = t * t;         double t3 = t2 * t;         double nt = 1.0 - t;         double nt2 = nt * nt;         double nt3 = nt2 * nt;         p.x = nt3 * points[0].x + 3.0 * t * nt2 * points[1].x + 3.0 * t2 * nt * points[2].x + t3 * points[3].x;         p.y = nt3 * points[0].y + 3.0 * t * nt2 * points[1].y + 3.0 * t2 * nt * points[2].y + t3 * points[3].y;     }; };   bool calculateSpline(const vector<Point2D> &values, vector<Segment> &bezier) {     int n = values.size() - 1;         if (n < 2)         return false;         bezier.resize(n);         Point2D tgL;     Point2D tgR;     Point2D cur;     Point2D next = values[1] - values[0];     next.normalize();         double l1, l2, tmp, x;         --n;         for (int i = 0; i < n; ++i)     {         bezier[i].points[0] = bezier[i].points[1] = values[i];         bezier[i].points[2] = bezier[i].points[3] = values[i + 1];                 cur = next;         next = values[i + 2] - values[i + 1];         next.normalize();                 tgL = tgR;                 tgR = cur + next;         tgR.normalize();                 if (abs(values[i + 1].y - values[i].y) < EPSILON)         {             l1 = l2 = 0.0;         }         else         {             tmp = values[i + 1].x - values[i].x;             l1 = abs(tgL.x) > EPSILON ? tmp / (2.0 * tgL.x) : 1.0;             l2 = abs(tgR.x) > EPSILON ? tmp / (2.0 * tgR.x) : 1.0;         }                 if (abs(tgL.x) > EPSILON && abs(tgR.x) > EPSILON)         {             tmp = tgL.y / tgL.x - tgR.y / tgR.x;             if (abs(tmp) > EPSILON)             {                 x = (values[i + 1].y - tgR.y / tgR.x * values[i + 1].x - values[i].y + tgL.y / tgL.x * values[i].x) / tmp;                 if (x > values[i].x && x < values[i + 1].x)                 {                     if (tgL.y > 0.0)                     {                         if (l1 > l2)                             l1 = 0.0;                         else                             l2 = 0.0;                     }                     else                     {                         if (l1 < l2)                             l1 = 0.0;                         else                             l2 = 0.0;                     }                 }             }         }                 bezier[i].points[1] += tgL * l1;         bezier[i].points[2] -= tgR * l2;     }         l1 = abs(tgL.x) > EPSILON ? (values[n + 1].x - values[n].x) / (2.0 * tgL.x) : 1.0;         bezier[n].points[0] = bezier[n].points[1] = values[n];     bezier[n].points[2] = bezier[n].points[3] = values[n + 1];     bezier[n].points[1] += tgR * l1;         return true; }   int main() {     vector<Point2D> testValues;     vector<Segment> spline;     Point2D p;       testValues.push_back(Point2D(0, 0));     testValues.push_back(Point2D(20, 0));     testValues.push_back(Point2D(45, -47));     testValues.push_back(Point2D(53, 335));     testValues.push_back(Point2D(57, 26));     testValues.push_back(Point2D(62, 387));     testValues.push_back(Point2D(74, 104));     testValues.push_back(Point2D(89, 0));     testValues.push_back(Point2D(95, 100));     testValues.push_back(Point2D(100, 0));       calculateSpline(testValues, spline);       for (auto s : spline)     {         for (int i = 0; i < RESOLUTION; ++i)         {             s.calc((double)i / (double)RESOLUTION, p);             cout << p.x << " " << p.y << endl;         }     }       cout << testValues.back().x << " " << testValues.back().y << endl;       return 0; }Bash1 g++ -std=c++11 TBezierInterpolation.cpp


textual

Код к задаче: «Перевести код из C++ в чистый Си - C (СИ)»

// TBezierInterpolation.c
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#include <stdbool.h>
#include <float.h>
 
#define RESOLUTION 32
#define  POINTS_LEN 10
 
typedef struct
{
    double x, y;
}Point2D;
 
 
Point2D Point2DAdd( Point2D *left,  Point2D *right)
{
    Point2D newPoint = {left->x + right->x, left->y + right->y};
    return newPoint;
}
Point2D Point2DSubtract( Point2D *left,  Point2D *right)
{
    Point2D newPoint = {left->x - right->x, left->y - right->y};
    return newPoint;
}
Point2D Point2DMultiply( Point2D *left, double v)
{
    Point2D newPoint = {left->x * v, left->y * v};
    return newPoint;
}
 
 
void Point2DNormalize(Point2D *point)
{
    double l = sqrt(point->x * point->x + point->y * point->y);
    point->x /= l;
    point->y /= l;
}
 
 
typedef struct
{
    Point2D points[4];
}Segment;
 
void SegmentCalc(Segment *seg,double t, Point2D *p)
{
    double t2 = t * t;
    double t3 = t2 * t;
    double nt = 1.0 - t;
    double nt2 = nt * nt;
    double nt3 = nt2 * nt;
    p->x = nt3 * seg->points[0].x + 3.0 * t * nt2 * seg->points[1].x + 3.0 * t2 * nt * seg->points[2].x + t3 * seg->points[3].x;
    p->y = nt3 * seg->points[0].y + 3.0 * t * nt2 * seg->points[1].y + 3.0 * t2 * nt * seg->points[2].y + t3 * seg->points[3].y;
}
 
 
bool CalculateSpline( Point2D values[], int valuesSize, Segment bezier[])
{
    int n = valuesSize - 1;
 
    if (valuesSize < 2)
        return false;
 
    Point2D tgL= {0.0,0.0};
    Point2D tgR= {0.0,0.0};
    Point2D cur= {0.0,0.0};
    Point2D next = Point2DSubtract(&values[1] ,&values[0]);
    Point2D tmpPoint= {0.0,0.0};
    Point2DNormalize(&next);
 
    double l1 = 0.0, l2= 0.0, tmp= 0.0, x= 0.0;
 
    --n;
 
    for (int i = 0; i < n; ++i)
    {
        bezier[i].points[0] = bezier[i].points[1] = values[i];
        bezier[i].points[2] = bezier[i].points[3] = values[i + 1];
 
        cur = next;
        next = Point2DSubtract(&values[i + 2],&values[i + 1]);
        Point2DNormalize(&next);
 
        tgL = tgR;
 
        tgR = Point2DAdd(&cur,&next);
        Point2DNormalize(&tgR);
 
        if (abs(values[i + 1].y - values[i].y) < DBL_EPSILON)
        {
            l1 = l2 = 0.0;
        }
        else
        {
            tmp = values[i + 1].x - values[i].x;
            l1 = abs(tgL.x) > DBL_EPSILON ? tmp / (2.0 * tgL.x) : 1.0;
            l2 = abs(tgR.x) > DBL_EPSILON ? tmp / (2.0 * tgR.x) : 1.0;
        }
 
        if (abs(tgL.x) > DBL_EPSILON && abs(tgR.x) > DBL_EPSILON)
        {
            tmp = tgL.y / tgL.x - tgR.y / tgR.x;
            if (abs(tmp) > DBL_EPSILON)
            {
                x = (values[i + 1].y - tgR.y / tgR.x * values[i + 1].x - values[i].y + tgL.y / tgL.x * values[i].x) / tmp;
                if (x > values[i].x && x < values[i + 1].x)
                {
                    if (tgL.y > 0.0)
                    {
                        if (l1 > l2)
                            l1 = 0.0;
                        else
                            l2 = 0.0;
                    }
                    else
                    {
                        if (l1 < l2)
                            l1 = 0.0;
                        else
                            l2 = 0.0;
                    }
                }
            }
        }
        tmpPoint = Point2DMultiply(&tgL , l1);
        bezier[i].points[1] = Point2DAdd(& bezier[i].points[1],&tmpPoint);
        tmpPoint = Point2DMultiply(&tgR , l2);
        bezier[i].points[2] = Point2DSubtract(& bezier[i].points[2],&tmpPoint);
    }
 
    l1 = abs(tgL.x) > DBL_EPSILON ? (values[n + 1].x - values[n].x) / (2.0 * tgL.x) : 1.0;
 
    bezier[n].points[0] = bezier[n].points[1] = values[n];
    bezier[n].points[2] = bezier[n].points[3] = values[n + 1];
    tmpPoint = Point2DMultiply(&tgR , l1);
    bezier[n].points[1] = Point2DAdd(& bezier[n].points[1],&tmpPoint);
 
    return true;
}
 
int main()
{
 
    Point2D testValues[POINTS_LEN] = {{0.0, 0.0},
                               {20.0, 0.0},
                               {45.0, -47.0},
                               {53.0, 335.0},
                               {57.0, 26.0},
                               {62.0, 387.0},
                               { 74.0, 104.0},
                              { 89.0, 0.0},
                             {95.0, 100.0},
                             { 100.0, 0.0} };
    Segment spline[100];
 
    Point2D p = {0.0,0.0};
 
 
    CalculateSpline(testValues,POINTS_LEN, spline);
 
    for(int i = 0; i < POINTS_LEN - 1;i++)
    {
        for (int j = 0; j < RESOLUTION; j++)
        {
            SegmentCalc(&spline[i],(double)j / (double)RESOLUTION, &p);
            printf("%lf %lf\n", p.x, p.y);
        }
    }
 
    printf("%lf %lf\n", testValues[POINTS_LEN - 1].x,testValues[POINTS_LEN - 1].y);
 
    return 0;
}

СДЕЛАЙТЕ РЕПОСТ

8   голосов, оценка 3.750 из 5



Похожие ответы
  1. Нужно что бы он считал количество заглавных буквC1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 #include #include #include #include void main() {     char s[250];     int i, kol = 0, kol1 = 0, j;     puts("Enter string");     fgets(s, 250, stdin); ("%s", s);     i = 0;     j = 0;     for (i = 0; i

  1. Перевести код из С++ в Си. Заранее спасибо!C++1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 #include "stdafx.h" #include "iostream" #include "cstring" #include "cstdlib" using namespace std;   int main(){  cout<<"Input text : ";  char* s = new char[1000];  cin.getline(s,1000);  for (int i=0; i

  1. C1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 #include #include #include char deletika(char a[80], long ot, long sk) {     int i, j, k = 0;     i = j = 0;     --ot;     sk = sk + ot;     do     {         if ((i < ot) || (i > sk))         {             a[j] = a[i];             j++;         }         i++;     } while (a[i] = '\0');     for (k = j; k <= i; k++)     {         a[k] = *"";     };     return (*a); } char zamenil(char a[80], long ot) {     int k = 0, k1 = 0;     char c[80], d[80];     char b[] = "123456789012345";     strcpy(c, a);     strcpy(d, a);     strcpy(c + ot, b);     k = strlen(c);     k1 = strlen(a);     for (int n = k1; n >= k; n--)         ;     {         c[n] = d[n];     }     for (n = 1; n <= k1; n++)     {         a[n] = c[n];     }     return (*a); } char qS(char a[80], int N) {     int i = 0, j = N;     char temp, p;     p = a[N];     do     {         while (a[i] > p)             i++;         while (a[j] < p)             j--;         if (i <= j)         {             temp = a[i];             a[i] = a[j];             a[j] = temp;             i++;             j--;         }     } while (i <= j);     if (j > 0)         qS(a, j);     if (N > i)         qS(a + i, N - i);     return (*a); } main() {     int j = 0;     clrscr();     char vvod[80];     FILE *fin, *fout;     fin = fopen("input.txt", "r");     fout = fopen("output.txt", "w");     printf("vvedite stroku\n");     fgets(vvod, 80, fin);     printf(vvod);     printf("-sobral\n");     deletika(vvod, 0, 15);     printf(vvod);     printf("-udalil\n");     while (vvod[j] != '\0')     {         j++;     };     printf(vvod);     printf("-propustil\n");     zamenil(vvod, 15);     printf(vvod);     printf("-zamenil\n");     qS(vvod, j - 1);     printf(vvod);     printf("-sortiroval\n");     fprintf(fout, vvod);     printf("vivod v file\n");     printf("and end");     getch();     fclose(fout);     return (0); }и ничего, печатает только -propustil zamenil и проч ничего не помогает

  1. Помогите пожалуйстаC++1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 #include "stdafx.h" #include #include using namespace std; double fix(double(*f)(double), double a, double b, double eps); double f(double x); int i;   int _tmain(int argc, _TCHAR* argv[]) {     setlocale(LC_ALL, "");//подключение языков     double a, b, eps;     cout << "Нахождение приближенного значения корня методом деления отрезка пополам.\nВведите левую границу отрезка 'a' = ";     cin >> a;//ввод левой границы отрезка 'a'     cout << "Введите правую границу отрезка 'b' = ";     cin >> b;//ввод правой границы отрезка 'b'     cout << "Введите точность нахождения 'eps' = ";     cin >> eps;//ввод точности нахождения 'eps'     cout << "Приближенное значение корня = " << fix(f, a, b, eps) << endl;     cout << "Приближенное значение корня найдено за " << i << " шагов" << endl;     system("PAUSE");     return 0; }   double fix(double(*f)(double), double a, double b, double eps) {     double x = (a + b) / 2;     while ((abs(b - a)>eps) && (f(x) != 0))     {         if (f(a)*f(x)<0)             b = x;         else             a = x;         x = (a + b) / 2;         cout << "x=" << x << endl;         i++;     }     return x; }   double f(double x) {     return sin(x);     }

  1. Суть в том,что надо проверь слова из строки на условия: 1)начало и конец слова начинается на одну и ту же букву 2)слово содержит 3 буквы к ошибки: 1) [Error] request for member 'length' in 'p', which is of non-class type 'char*' 2 )26строка expected primary-expression before 'int' 3)26строка expected ')' before 'int' 4) 30строка expected ')' before 'p' 5)30строка expected ')' before ';' tokenC1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 #include #include #include #include #include   int  cnt(char text,char ch)  {     int res = 0;     for (; text; ++text) {         res += (text == 'k');     }     return res; }     int main() {     char text[256], *p;       fgets(text, sizeof(text), stdin);       p = strtok(text, " ");     while (p)     {         if ((p[0] == p[p.length()-1]) && (3==(int cnt(text,'k'))))         {             printf("%s\n", p);         }         p = strtok(NULL, " ");     }       return 0; }

  1. Доброго времени суток! Появилось желание реализовать в учебных целях библиотеку для связанных списков, очередей, стеков. Возник ряд вопросов. 1. Как реализовать эти библиотеки универсальными, чтобы они принимали в качестве своих элементов данные любого формата. Например, чтобы можно было бы организовывать очереди не только из целых чисел, но и различных структур данных. 2. Как подойти к процессу проектирования интерфейса библиотеки? Возможно, есть какая-та литература по вопросам проектирования ПО? В практике пока не очень силен.

  1. C1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 #include   int main(void) { int k; float p,s,norm;   printf("vvedite p: "); scanf("%f",p); norm,s=10; k=1; while (s<=200) { norm=norm*(p/100+1); s=s+norm; k++;   }   printf("колличество дней: ",k); printf("cуммарный пробег",s);   return 0; }(впервые пишу в СИ)

  1. Дано 7 чисел, считает количество отрицательных и сумму положительных. Тремя способами (for, while, do while). Но здесь я точнее не знаю как sizeof заменить на си. C++1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 #include "stdafx.h" #include "stdlib.h" #include #include #include #include #include int array[7]; void main() {     int i, sum, count;     setlocale(LC_ALL, "RUS");     system("cls");     printf(" Написать 7 чисел и программа тремя способами считает количество отрицательных и сумму положительных. \n \n Введите 7 чисел массива: ");     for (i = 0; i < sizeof(array) / sizeof(int); i++)         scanf("%d", &array[i]);     printf("\n Вывод массива:");     for (i = 0; i < sizeof(array) / sizeof(int); i++)         printf("%5d", array[i]);     sum = 0; count = 0;     for (i = 0; i < sizeof(array) / sizeof(int); i++)     {         if (array[i] > 0) sum += array[i];         else count++;     }     printf("\n\n Цикл For \n");     printf(" Сумма положительных: %d \n", sum);     printf(" Число отрицательных: %d \n", count);     i = 0; sum = 0; count = 0;     while (i < sizeof(array) / sizeof(int))     {         if (array[i] > 0) sum += array[i];         else count++;         i++;     }     printf("\n Цикл While \n");     printf(" Сумма положительных: %d \n", sum);     printf(" Число отрицательных: %d \n", count);     i = 0; sum = 0; count = 0;     do     {         if (array[i] > 0) sum += array[i];         else count++;         i++;     } while (i < sizeof(array) / sizeof(int));     printf("\n Цикл Do While \n");     printf(" Сумма положительных: %d \n", sum);     printf(" Число отрицательных: %d \n", count);     _getch(); }Возможно, применить это:C1 2 3 4 5 6 7 8 9 10 11 12 13 14 int x, sum, k; . . . sum=0; k=0; for (i = 0; i <7; i++) { scanf_s("%d \n", &x); if(x>0) sum=sum+x; else k++; } printf(" Сумма положительных: %d \n", sum); printf(" Число отрицательных: %d \n", k);Но у меня как то не получается.

  1. C1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 #include "stdafx.h" #include #include #include #include   using namespace std;   int main() {     char ext;     do {         char r = 0;         int a = 0, b = 0, c = 0, D;         double x1, x2;         printf("a=");         scanf_s("%d", &a);         printf("\nb=");         scanf_s("%d", &b);         printf("\nc=");         scanf_s("%d", &c);             D = b*b - 4 * a * c;         if (D < 0) printf("Korney net.");         else {             x1 = (-b - sqrt((double)D)) / 2 * a;             x2 = (-b + sqrt((double)D)) / 2 * a;             printf("x1=%f\nx2=%f\n", x1, x2);         }         printf("continue?(y/n)\n");         scanf_s("%s", &ext);         //if (r = 'y')ext = 1;         //if (r = 'n')ext = 0;         getchar();         } while (ext == 'y');       getchar();     return 0; }