Example #1
0
func dgesddHelper(m, n int, a []float64, lda int, s, u []float64, ldu int, vt []float64, ldvt int, work []float64, lwork int, iwork []C.integer) error {
	var (
		jobz_  = C.char('S')
		m_     = C.integer(m)
		n_     = C.integer(n)
		a_     = ptrFloat64(a)
		lda_   = C.integer(lda)
		s_     = ptrFloat64(s)
		u_     = ptrFloat64(u)
		ldu_   = C.integer(ldu)
		vt_    = ptrFloat64(vt)
		ldvt_  = C.integer(ldvt)
		work_  = ptrFloat64(work)
		lwork_ = C.integer(lwork)
		iwork_ = ptrInt(iwork)
	)
	var info_ C.integer

	C.dgesdd_(&jobz_, &m_, &n_, a_, &lda_, s_, u_, &ldu_, vt_, &ldvt_, work_, &lwork_, iwork_, &info_)

	info := int(info_)
	switch {
	case info < 0:
		return errInvalidArg(-info)
	case info > 0:
		return errFailConverge(info)
	default:
		return nil
	}
}
Example #2
0
func Dgesdd(jobz string, M, N int, A []float64, lda int, S []float64, U []float64,
	ldu int, Vt []float64, ldvt int) int {

	var info int = 0
	var lwork int = -1
	var work float64

	cjobz := C.CString(jobz)
	defer C.free(unsafe.Pointer(cjobz))

	iwork := make([]int, 8*min(M, N))

	// pre-calculate work buffer size
	C.dgesdd_(cjobz, (*C.int)(unsafe.Pointer(&M)), (*C.int)(unsafe.Pointer(&N)),
		nil, (*C.int)(unsafe.Pointer(&lda)),
		nil, nil, (*C.int)(unsafe.Pointer(&ldu)),
		nil, (*C.int)(unsafe.Pointer(&ldvt)),
		(*C.double)(unsafe.Pointer(&work)), (*C.int)(unsafe.Pointer(&lwork)),
		(*C.int)(unsafe.Pointer(&iwork[0])),
		(*C.int)(unsafe.Pointer(&info)))

	// allocate work area
	lwork = int(work)
	wbuf := make([]float64, lwork)

	var Ubuf, Vtbuf *C.double
	if U != nil {
		Ubuf = (*C.double)(unsafe.Pointer(&U[0]))
	} else {
		Ubuf = (*C.double)(unsafe.Pointer(nil))
	}
	if Vt != nil {
		Vtbuf = (*C.double)(unsafe.Pointer(&Vt[0]))
	} else {
		Vtbuf = (*C.double)(unsafe.Pointer(nil))
	}

	C.dgesdd_(cjobz, (*C.int)(unsafe.Pointer(&M)), (*C.int)(unsafe.Pointer(&N)),
		(*C.double)(unsafe.Pointer(&A[0])), (*C.int)(unsafe.Pointer(&lda)),
		(*C.double)(unsafe.Pointer(&S[0])), Ubuf, (*C.int)(unsafe.Pointer(&ldu)),
		Vtbuf, (*C.int)(unsafe.Pointer(&ldvt)),
		(*C.double)(unsafe.Pointer(&wbuf[0])), (*C.int)(unsafe.Pointer(&lwork)),
		(*C.int)(unsafe.Pointer(&iwork[0])),
		(*C.int)(unsafe.Pointer(&info)))

	return info
}