2012-02-28 5 views
1

Я очень новичок в C, но знаю свой путь вокруг [R]. Эта ошибка может быть очень глупой ошибкой в ​​C.поймал segfault в функции [R]

Мой код C делает сглаживание ядра.

* Когда я прокомментирую последнюю строку кода, моя функция работает: результаты [i] = v; *

Этот вызов убивает R:

< new.y -zsmooth2 (X = C (0: 80000), xpts = $ V2, DAT, ypts = $ DAT В4, ч = 10000)

* пойманы * выдаёт ошибку сегментации адрес 0x1184f8000, потому что 'память не отображается'

TraceBack: 1: .C ("kernel_smooth", as.double (х), as.double (YP ts), as.double (xpts), as.integer (n), as.integer (nxpts), as.double (h), result = double (length (xpts))) 2: zsmooth2 (x = c (0: 80000), xpts = DAT $ V2, ypts = DAT $ В4, ч = 10000)

С-код:

#include <R.h> 
#include <Rmath.h> 
#include <stdio.h> 


void kernel_smooth(double *x, double *ypts, double *xpts, int *n, int *nxpts, double *h, double *results){ 
    int i, j; 

    for(i = 0; i < *n; i++){ 

     double nsum = 0; 
     double dsum = 0; 

     double z = x[i] + *h; 
     double y = x[i] - *h; 

     for(j = 0; j < *nxpts; j++){ 

      if(xpts[j] < y){ 
       continue; 
      } 
      if(xpts[j] > z){ 
       break; 
      } 
      double d = (xpts[j] - i)/*h; 
      double r = dnorm(d, 0, 1, 0); 
      nsum += r * ypts[j]; 
      dsum += r; 
     } 
      Rprintf("test:i %d\n", i); 
      double v = nsum/dsum; 
      Rprintf("test:v %f\n", v); 

     results[i] = v; 
    } 

} 

R-код:

dyn.load("~/github/ZevRTricks/smoother1.so") 
zsmooth2<-function(x, ypts, xpts, h){ 
    n <- length(x) 
    nxpts <- length(xpts) 
    dens <- .C("kernel_smooth", as.double(x), as.double(ypts), 
       as.double(xpts), as.integer(n), as.integer(nxpts), 
       as.double(h), result = double(length(xpts))) 
dens[["result"]] 
} 
+0

У вас есть код C, размещенный на форуме C# .. – MethodMan

+0

C и C# - два совершенно разных языка. Вы не просто используете их имена взаимозаменяемо. – BoltClock

+0

Насколько мне известно, вы не можете легко использовать C# с R. Так действительно ли код C? –

ответ

2

xpts и ypts являются векторами, а в вашем коде на C вы пытаетесь получить доступ к элементам 1 до n в каждом из них. n - длина x, что в 100 раз больше в вашем втором примере, чем в первом примере. Сравните seq(from = 0, to = 80000 by = 100) с 0:80000, (и пока вы на нем, вы можете сбросить c() со всего 0:80000).

Так что я думаю, что xpts и ypts - это как минимум 801 элементов длиной, но менее 80001 элементов. Вы где-то испортили свою индексацию.

Обратите внимание, что вы передаете x вашему коду C, но на самом деле не используете его ни для чего.

+0

Не проверял, но я уверен, что вы правы. Могу ли я спросить, как я могу вернуть индекс (для массива) для значений больше х и меньше, чем у? –

+0

Если вы говорите о цикле for в C, что-то вроде 'for (i = x; i Tyler

+0

Спасибо за вашу помощь, однако все еще поймаем ошибку после исправления моего кода. Я обновил его выше. –

Смежные вопросы