#include <bits/stdc++.h>
using namespace std;

using ll=long long;
#define rep(i,n) for(int i=0;i<n;i++)
#define all(a) a.begin(),a.end()

const double EPS=1E-15;
constexpr int gcd(int a,int b){return b?gcd(b,a%b):a;}

struct v{
	int x,y,z,g;
	double L2,nx,ny,nz;
	bool operator==(const v&r)const{return this->x==r.x and this->y==r.y and this->z==r.z and this->g==r.g;};
	void setData(){
	    g=gcd(x,gcd(y,z));
        L2=sqrt(x*x+y*y+z*z)/g;
        nx=x/g/L2;
        ny=y/g/L2;
        nz=z/g/L2;
	}
	friend ostream& operator<<(ostream&os,const v&p);
};

bool operator<(const v&l,const v&r){return l.nx<r.nx or (l.nx==r.nx and (l.ny<r.ny or (l.ny==r.ny and l.nz<r.nz)));};
ostream& operator<<(ostream&os, const v&p){os<<p.x<<" "<<p.y<<" "<<p.z; return os;};

v makeData(int X, int Y, int Z){
	v ret;
	ret.x=X, ret.y=Y, ret.z=Z;
	ret.setData();
	return ret;
}

bool same(v a,v b){
    return a.x/a.g==b.x/b.g and a.y/a.g==b.y/b.g and a.z/a.g==b.z/b.g;
}

bool cmp(v a,v b){
	return a.x<b.x or (b.x==a.x and (a.y<b.y or (b.y==a.y and a.z<b.z)));
}

double dist(v a, v b){
    if(same(a,b)) return 10000; 
    return sqrt((b.nx-a.nx)*(b.nx-a.nx) + (b.ny-a.ny)*(b.ny-a.ny) + (b.nz-a.nz)*(b.nz-a.nz));
}


using data=pair<double,pair<v,v>>;
data closest_pair(vector<v> vec){
    if(vec.size()<=1) return {10000,{v(),v()}};
    if(vec.size()==2){
		if(cmp(vec[1],vec[0])){
			//cout<<"Ret (2) :"<<vec[1]<<" "<<vec[0]<<" = "<<dist(vec[0],vec[1])<<endl;
			return {dist(vec[0],vec[1]),{vec[1],vec[0]}};
		}else{
			//cout<<"Ret (2) :"<<vec[0]<<" "<<vec[1]<<" = "<<dist(vec[0],vec[1])<<endl;
			return {dist(vec[0],vec[1]),{vec[0],vec[1]}};
		}
	}
    vector<v> vs1,vs2,vs3;
    int index=vec.size()/2;
    double sep=vec[index].nx;
    copy(vec.begin(), vec.begin()+index, back_inserter(vs1));
    copy(vec.begin()+index, vec.end(), back_inserter(vs2));
    
	data s1=closest_pair(vs1), s2=closest_pair(vs2), minDist;
	if(fabs(s1.first-s2.first)>EPS){
		minDist=min(s1,s2);
	}else{
		if(cmp(s1.second.first,s2.second.first) or (s1.second.first==s2.second.first and cmp(s1.second.second,s2.second.second))){
			minDist=s1;
		}else{
			minDist=s2;
		}
	}
    
    sort(all(vec),[](v a,v b){return a.ny<b.ny;});
    
    for(auto d:vec){
        if(fabs(d.nx-sep)>=minDist.first) continue;
        for(int i=vs3.size()-1;i>=0;i--){
            double dst=dist(vs3[i],d);
			//if(dst>minDist.first)break;
			v n1=vs3[i],n2=d;
			if(cmp(n2,n1))swap(n1,n2);
			if(fabs(minDist.first-dst)<EPS){
				if(cmp(n1,minDist.second.first) or (n1==minDist.second.first and cmp(n2,minDist.second.second))){
					//cout<<"   "<<n1<<" "<<n2<<endl;
					minDist={dst,{n1,n2}};
				}
			}else if(dst<minDist.first){
				//cout<<"   "<<n1<<" "<<n2<<endl;
                minDist={dst,{n1,n2}};
            }
        }
        vs3.push_back(d);
    }
	//cout<<"Ret ("<<vec.size()<<") :"<<minDist.second.first<<" "<<minDist.second.second<<" = "<<minDist.first<<endl;
    return minDist;
    
}

int main(){
	ios::sync_with_stdio(false);
	cin.tie(0);
	
	int m,n,s,w;
	while(cin>>m>>n>>s>>w, m or n){
		vector<v> vec;
		rep(i,m){
			int x,y,z;
			cin>>x>>y>>z;
			vec.push_back(makeData(x,y,z));
		}
		int g=s;
		rep(i,n) {
			vec.push_back(makeData((g/7)%100+1, (g/700)%100+1, (g/70000)%100+1));
			if(g%2==0)g/=2;
			else g=(g/2) xor w;
		}
	    sort(all(vec),[](v a,v b){return a.nx<b.nx;});
		vec.erase(unique(all(vec),same),vec.end());
		//for(auto d:vec)cout<<d<<"("<<d.nx<<")"<<endl;
		//cout<<"===="<<endl;
	    data ans=closest_pair(vec);
	    v a1=ans.second.first;
	    v a2=ans.second.second;
	    if(cmp(a2,a1)) swap(a1,a2);
	    cout<<a1<<" "<<a2<<endl;
	}
	return 0;
}



Measured memory_bytes: 25824